Take the 2-minute tour ×
WordPress Development Stack Exchange is a question and answer site for WordPress developers and administrators. It's 100% free, no registration required.

I created a Custom Post Type: Product and a Taxonomy assigned to it: Products

So under that Taxonomy I can add different types of products (terms if i'm not mistaken).

When adding new products I get to choose the different terms where it belongs or add new ones.

I want to add this terms to the main navigation menu under 'Products'. As a dropdown in a hierarchical way.

I've tried with custom walker following this example but that displays posts, i need terms in a hierarchical way. Also tried modifying the code but can't make it work, tried add_filter with wp_nav_menu_items to add items to the menu, but it just doesn't work, I don't know the properties of the items objects.

Edit

I had a breakthrough using add_filter and a custom category walker, but it only shows first level.

When I need to display in tree mode:

  • Products
    • A
    • B
      • B-1
    • C
      • C-1
      • C-2
      • C-3

Custon nav walker

class top_bar_walker extends Walker_Nav_Menu {

function display_element( $element, &$children_elements, $max_depth, $depth=0, $args, &$output ) {
    $element->has_children = !empty( $children_elements[$element->ID] );
    $element->classes[] = ( $element->current || $element->current_item_ancestor ) ? 'active' : '';
    $element->classes[] = ( $element->has_children && $max_depth !== 1 ) ? 'has-dropdown' : '';

    parent::display_element( $element, $children_elements, $max_depth, $depth, $args, $output );
}

function start_el( &$output, $object, $depth = 0, $args = array(), $current_object_id = 0 ) {
    $item_html = '';
    parent::start_el( $item_html, $object, $depth, $args ); 

    $output .= ( $depth == 0 ) ? '<li class="divider"></li>' : '';

    $classes = empty( $object->classes ) ? array() : (array) $object->classes;

    if( in_array('label', $classes) ) {
        $output .= '<li class="divider"></li>';
        $item_html = preg_replace( '/<a[^>]*>(.*)<\/a>/iU', '<label>$1</label>', $item_html );
    }

if ( in_array('divider', $classes) ) {
    $item_html = preg_replace( '/<a[^>]*>( .* )<\/a>/iU', '', $item_html );
}

    $output .= $item_html;
}

function start_lvl( &$output, $depth = 0, $args = array() ) {
    $output .= "\n<ul class=\"sub-menu dropdown\">\n";
}

}

Filter

add_filter('wp_nav_menu_items','add_menu_products');

function add_menu_products($items) {

            $args = array(
                'show_option_all'    => null,
                'orderby'            => 'name',
                'order'              => 'ASC',
                'style'              => 'list',
                'show_count'         => 0,
                'hide_empty'         => 0,
                'use_desc_for_title' => 0,
                'child_of'           => 0,
                'feed'               => '',
                'feed_type'          => '',
                'feed_image'         => '',
                'exclude'            => '',
                'exclude_tree'       => '',
                'include'            => '',
                'hierarchical'       => 1,
                'title_li'           => null,
                'show_option_none'   => __( 'No categories' ),
                'number'             => null,
                'echo'               => 0,
                'depth'              => 0,
                'current_category'   => 0,
                'pad_counts'         => 0,
                'taxonomy'           => 'products',
                'walker'             => new Categorias_Menu_Walker()
            );

             $cat_menu = wp_list_categories( $args );

$items = '<li class="menu-item menu-item-type-taxonomy menu-item-object-category menu-item-has-children has-dropdown menu-item-120 not-click">
<a href="http://localhost/patmaq/productos/">Productos</a>
<ul class="sub-menu dropdown">'.$cat_menu.'</ul></li>' . $items;
return $items;
}

As you can see I had to hard code the menu item 'Productos' and add the sub-items to it.

And the custom category walker assigned to it

class Categorias_Menu_Walker extends Walker_Category {
function display_element( $element, &$children_elements, $max_depth, $depth=0, $args, &$output ) {
    $id_field = $this->db_fields['id'];
    $id = $element->$id_field;
    $this->has_children = !empty( $children_elements[ $id ] );
    //$element->classes[] = ( $element->current || $element->current_item_ancestor ) ? 'active' : '';
    $element->classes[] = ( ($max_depth == 0 || $max_depth > $depth+1 ) && isset( $children_elements[$id]) ) ? 'has-dropdown' : '';

    parent::display_element( $element, $children_elements, $max_depth, $depth, $args, $output );
}
function start_el( &$output, $category, $depth = 0, $args = array(), $id = 0 ) {

    $item_html = '';
    parent::start_el( $item_html, $category, $depth, $args ); 

    $classes = empty( $category->classes ) ? array() : (array) $category->classes;

    if( in_array('label', $classes) ) {
        $output .= '<li class="divider"></li>';
        $item_html = preg_replace( '/<a[^>]*>(.*)<\/a>/iU', '<label>$1</label>', $item_html );
    }

if ( in_array('divider', $classes) ) {
    $item_html = preg_replace( '/<a[^>]*>( .* )<\/a>/iU', '', $item_html );
}

    $output .= $item_html;

}
function start_lvl(&$output, $depth=0, $args=array()) {  
    $output .= "\n<ul class=\"sub-menu dropdown\">\n";  
}  
function end_lvl(&$output, $depth=0, $args=array()) {  
    $output .= "</ul>\n";  
}  
}

In case this helps, i'm using FoundationPress's theme.

Hope someone can help me out, thanks!

share|improve this question

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Browse other questions tagged or ask your own question.