Ajouter un déambulateur personnalisé à un menu créé dans un widget

10

Je sais comment ajouter un Walker à un menu personnalisé créé par le thème (menu nommé primarydans cet exemple), mais comment puis-je cibler un menu créé dans un widget avec le widget de menu personnalisé wordpress par défaut?

if ( has_nav_menu( 'primary' ) ) {

$args = array(
    'menu' => 'main-menu',
    'menu_id' => 'main-menu',
    'theme_location' => 'primary',
    'depth' => 0,
    'container' => false,
    'menu_class' => 'nav',
    'walker' => new Myprefix_Walker_Nav_Menu(),
    'echo' => 0
);

$nav = wp_nav_menu( $args );

}
amy
la source

Réponses:

14

Si vous regardez l'implémentation de la WP_Nav_Menu_Widgetclasse, vous verrez le code suivant:

function widget($args, $instance) {
    // Get menu
    $nav_menu = ! empty( $instance['nav_menu'] ) ? wp_get_nav_menu_object( $instance['nav_menu'] ) : false;

    if ( !$nav_menu )
        return;

    $instance['title'] = apply_filters( 'widget_title', empty( $instance['title'] ) ? '' : $instance['title'], $instance, $this->id_base );

    echo $args['before_widget'];

    if ( !empty($instance['title']) )
        echo $args['before_title'] . $instance['title'] . $args['after_title'];

    wp_nav_menu( array( 'fallback_cb' => '', 'menu' => $nav_menu ) );

    echo $args['after_widget'];
}

Cela signifie qu'il n'y a aucune chance d'accrocher un menu. Vous devez donc jeter un œil à wp_nav_menul'implémentation de la fonction, où vous pouvez trouver les lignes de code suivantes:

$defaults = array(
  'menu' => '',
  'container' => 'div',
  'container_class' => '',
  'container_id' => '',
  'menu_class' => 'menu',
  'menu_id' => '',
  'echo' => true,
  'fallback_cb' => 'wp_page_menu',
  'before' => '',
  'after' => '',
  'link_before' => '',
  'link_after' => '',
  'items_wrap' => '<ul id="%1$s" class="%2$s">%3$s</ul>',
  'depth' => 0,
  'walker' => '',
  'theme_location' => ''
);

$args = wp_parse_args( $args, $defaults );
$args = apply_filters( 'wp_nav_menu_args', $args );
$args = (object) $args;

Ici, vous pouvez voir que tous les arguments passés à la wp_nav_menufonction peuvent être remplacés. Donc, ce dont vous avez besoin est de créer votre propre gestionnaire de hook qui ajoutera votre déambulateur à un menu de navigation. Cela pourrait être simple:

function myplugin_custom_walker( $args ) {
    return array_merge( $args, array(
        'walker' => new My_Custom_Walker(),
        // another setting go here ... 
    ) );
}
add_filter( 'wp_nav_menu_args', 'myplugin_custom_walker' );
Eugene Manuilov
la source
c'est super merci. On dirait que cela fait la valeur par défaut pour tous les menus. Ai-je raison de supposer que lorsque j'utilise cela, je suis coincé avec tous les menus ayant cette marchette? parce que j'ai essayé 'walker' => new Walker_Nav_Menu()dans les arguments de mon menu spécifique de le remplacer à nouveau pour devenir le marcheur par défaut de wordpress pour un seul menu, mais malheureusement cela ne fonctionne pas.
amy
@amy oui ce sera par défaut pour tous les menus.
Eugene Manuilov
@amy vous pouvez inclure du code pour examiner les arguments. Mettez ensuite une condition si vous appliquez ou non le déambulateur.
Wayne
4

En développant la réponse de @ Eugene, si vous souhaitez limiter cela à un menu spécifique, vérifiez simplement le terme ID du menu:

function custom_nav_args($args){
$menu = $args['menu'];
    if($menu->term_id === 17)  /* replace term_id with menu id, or use $menu->name to do it by menu name*/
    {
        $args['walker'] = new My_Custom_Walker();
    }
    return $args;
}
add_filter('wp_nav_menu_args', 'custom_nav_args');
Yaron
la source
Comment filtrerions-nous par identifiant de la barre latérale?
Steven Vachon
1

C'est une alternative au ciblage d'un menu par term_idet j'ai pensé que cela pourrait être utile à quelqu'un comme moyen de modifier plusieurs menus sans avoir à rechercher leurs identifiants.

En ajoutant print_r($args)à un filtre, j'ai remarqué qu'il $args['menu']s'agit d'une chaîne pour les menus dans des emplacements de thème prédéfinis et WP_Term_Objectpour un widget de menu personnalisé dans une barre latérale.

Je l'ai utilisé pour cibler les menus par slug et ajouter une classe à leur conteneur. Un certain nombre de menus peuvent être ciblés en incluant une chaîne commune dans leurs slugs. Remarque: le slug de menu provient de la clé du tableau register_nav_menus().

function my_menu_thingy( $args ) {
  if( is_object($args['menu']) && strpos($args['menu']->{slug},'my-common-string') !== false ) {
    $args['walker'] = new My_Custom_Walker();
  }
  return $args;
}
add_filter( 'wp_nav_menu_args', 'my_menu_thingy' );

Pour un seul menu, il vous suffit de vérifier cela $args['menu']->{slug} == 'your-slug'au lieu du bit strpos () ci-dessus.

Jon
la source
1

Vous pouvez ajouter un déambulateur personnalisé à un menu de navigation créé dans un widget à l'aide du widget_nav_menu_argsfiltre ajouté dans wordpress 4.2.0. Il accepte quatre arguments (voir wp-includes/widgets/class-wp-nav-menu-widget.php). Mais pour ajouter uniquement un marcheur personnalisé, il vous suffit d'utiliser le premier argument, de la même manière que vous utilisez le wp_nav_menu_argsfiltre.

    add_filter('wp_nav_menu_args', 'my_args'); //for menus
    add_filter('widget_nav_menu_args', 'my_args'); //for menus in widgets
    function my_args($args) { //$args is only argument needed to add custom walker
       return array_merge( $args, array(
          'walker' => new My_Custom_Walker(),
       ) );
    }
celleness
la source