Home

Traditional sub navigation menu to WordPress

This example adds a submenu parameter to the wp_nav_menu function. When the submenu parameter is set to true wp_nav_menu function shows items in the second level and down in the current location. This way you can create a traditional secondary menu by using only one WP menu.

Add following code to functions.php file in theme or subtheme.

class SubMenuNavigvation {
	
	public static $currentID = 0;

	function __construct() {
		add_filter( 'wp_nav_menu_objects', array($this, 'submenu_limit'), 10, 2 );		
	}

	function submenu_limit( $items, $args ) {

		if ( empty( $args->submenu ) || empty( $args->theme_location ) ) {
			return $items;
		}

		foreach ( $items as $key => $item ) {
			if ( $item->current ) {
				SubMenuNavigvation::$currentID = $item->ID;
				break;
			}
		}

		$subMenuTitle = $this->get_roottitle($args->theme_location);		
		$ids       = wp_filter_object_list( $items, array( 'title' => $subMenuTitle ), 'and', 'ID' );
		
		$parent_id = array_pop( $ids );
		$children  = $this->submenu_get_children_ids( $parent_id, $items );
	
		foreach ( $items as $key => $item ) {
			if ( ! in_array( $item->ID, $children ) ) {
				unset( $items[$key] );
			}
		}
		return $items;
	}
	
	function submenu_get_children_ids( $id, $items ) {
		$ids = wp_filter_object_list( $items, array( 'menu_item_parent' => $id ), 'and', 'ID' );
		foreach ( $ids as $id ) {
			$ids = array_merge( $ids, $this->submenu_get_children_ids( $id, $items ) );
		}
		return $ids;
	}

	private static function get_roottitle($theme_location) {
            
		if ( ( $locations = get_nav_menu_locations() ) && isset( $locations[ $theme_location ] ) ) { 
			$menu = wp_get_nav_menu_object( $locations[ $theme_location ] ); 
			$items = wp_get_nav_menu_items($menu->term_id);
			
			$title = "";
			foreach($items as $item) {
				if(SubMenuNavigvation::$currentID == $item->ID){
					$title = SubMenuNavigvation::getNext($items, $item->menu_item_parent, $item->title);
				}
			}
			return $title;
		}
		return "";
	}
	
	private static function getNext($items, $idparent, $ret)
	{
		foreach($items as $item) {
			if($idparent == $item->ID){                     
				$ret = $item->title;
				SubMenuNavigvation::getNext($items, $item->menu_item_parent, $item->title);
			}
		}
		return $ret;
	}

}
$SubMenuNavigvation = new SubMenuNavigvation();

And here is code to add a submenu to the template.

        wp_nav_menu(
            array(
                'theme_location' => 'primary-menu',                 
                'submenu' => true,
                'echo' => true 
            )
        );

Leave a Reply

Your email address will not be published.