Mise en évidence wp_nav_menu () Ancêtre classe w / o Les enfants dans la structure de navigation?

wordpress.stackexchange https://wordpress.stackexchange.com/questions/3014

  •  16-10-2019
  •  | 
  •  

Question

( Note Modérateurs: a été initialement intitulé "wp_nav_menu classe Ancêtre sans enfants dans la structure de navigation")

J'ai un wp_nav_menu dans ma tête qui avait trois pages en elle. Quand je suis sur un de ces pages, la li contenant cette page dans le menu obtient la .current_page_item de classe. Ces trois pages ont des modèles, et ces modèles contiennent des requêtes personnalisées pour obtenir tous les messages d'un certain type de contenu. En effet, la perception « enfants » de cette page de premier niveau ne sont pas réellement des enfants, ils sont juste un type de contenu que je suis associé à cette page de niveau supérieur à l'aide d'un modèle.

Je voudrais les éléments de menu de niveau supérieur pour obtenir une classe de 'current-ancestor' lorsque l'utilisateur navigue sur une seule page d'un type de poste spécifique, encore une fois, associée à cette page que dans une requête personnalisée dans le fichier modèle.

L'espoir qui fait sens - sinon, laissez-moi savoir où je vous ai perdu! Très reconnaissants d'aide.

- Edité pour plus de détails: Par exemple, j'ai une page statique appelée Ateliers qui utilise un modèle. Son limace est ateliers . Le modèle a une fonction de get_posts personnalisés et boucle à l'intérieur, ce qui tractions et affiche tous les messages d'un type de contenu personnalisé appelé ateliers . Si je clique sur l'un des titre de ces ateliers, je suis pris au contenu complet de ce morceau de contenu. La structure permalien du type de poste personnalisé est mis à des ateliers / postname , de sorte que l'utilisateur voit, ces morceaux de contenu sont des enfants de la page Ateliers, alors qu'en réalité ils sont tous d'un contenu type, mais sans lien avec la page. Il est cette lacune que je dois fermer efficacement dans le menu, mettant en lumière l'élément de menu « Ateliers » lorsque le contenu de navigation de type « atelier ».

Encore une fois, l'espoir qui fait sens, je pense que je l'ai dit « atelier » plus de 20 fois dans un paragraphe!

Était-ce utile?

La solution

Il y a une solution plus simple. Oubliez la création de pages pour chaque type de poste pour que vous puissiez avoir des éléments nav, parce que vous avez appris, WP n'a aucun moyen de reconnaître que les types personnalisés que vous parcourez sont liés à cette page.

, créez la place un lien personnalisé dans Apparence-> Menus. Il suffit de mettre l'URL qui renverra votre type personnalisé et lui donner une étiquette, puis appuyez sur « Ajouter au menu ».

http://example.com/workshops/

ou non-pretty-permaliens:

http://example.com/?post_type=workshops

ce seul sera tout simplement créer un bouton de navigation qui affiche tous les messages avec ce type de poste personnalisé, et ajoutera également la classe actuelle-élément de menu lorsque vous avez cliqué sur cet élément nav - mais il ne sera pas encore ajouter la classe de navigation sur une URL autre que celui-ci

Ensuite, une fois qu'il est créé, allez dans la configuration de ce nouvel élément, et entrez la limace du type de poste personnalisé dans le champ « attribut title » (vous pouvez aussi utiliser le champ de description, mais que l'on est caché dans la Options de l'écran admin par défaut).

Maintenant, vous devez brancher le filtre à nav_menu_css_class (qui obtient tiré pour chaque élément de navigation) et vérifier si le contenu en cours est du type poste indiqué dans votre article de navigation personnalisé:

add_filter('nav_menu_css_class', 'current_type_nav_class', 10, 2 );
function current_type_nav_class($classes, $item) {
    $post_type = get_query_var('post_type');
    if ($item->attr_title != '' && $item->attr_title == $post_type) {
        array_push($classes, 'current-menu-item');
    };
    return $classes;
}

Dans ce cas, nous allons vérifier que le contenu du champ d'attribut de titre ne sont pas vides et si elles correspondent au courant post_type interrogée. Si oui, nous ajoutons la classe actuelle-élément de menu à son tableau de classe, puis retourne le tableau modifié.

Vous pouvez modifier cela pour correspondre simplement le titre de l'élément de navigation, mais si pour une raison quelconque vous voulez titre l'élément de navigation différemment que la limace plaine du type poste, en utilisant l'attribut Titre ou champ Description vous donne cette flexibilité .

Maintenant, chaque fois que vous visionnez un seul élément (ou probablement même des listes d'archives) d'un type de poste qui correspond à un élément de menu de navigation, cet élément sera donné la classe CSS courant élément de menu afin que votre mise en surbrillance fonctionnera.

pages Non ou modèles de page nécessaire ;-) La requête URL prend soin d'aller chercher les bons messages. Votre modèle de boucle se charge d'afficher la requête de sortie. Cette fonction prend soin de reconnaître ce qui est montré et en ajoutant la classe CSS.

BONUS

Vous pouvez même automatiser le processus en utilisant wp_update_nav_menu_item, en ayant des éléments de menu générés automatiquement pour tous vos types de poste. Pour cet exemple, vous devez d'abord avoir récupéré le $menu_id du menu de navigation que vous voulez cet article ont ajouté à.

$types = get_post_types( array( 'exclude_from_search' => false, '_builtin' => false  ), 'objects' );
foreach ($types as $type) {
    wp_update_nav_menu_item( $menu_id, 0, array(
        'menu-item-type' => 'custom',
        'menu-item-title' => $type->labels->name,
        'menu-item-url' => get_bloginfo('url') . '/?post_type=' . $type->rewrite['slug'],
        'menu-item-attr-title' => $type->rewrite['slug'],
        'menu-item-status' => 'publish'
        )
    );
}

Autres conseils

au lieu d'utiliser

  

$ post_type =   get_query_var ( 'post_type');

Vous pouvez essayer:

  

$ post_type = get_post_type ();

Somtimes le type poste n'est pas définie dans la requête var. Tel est le cas pour la post_type par défaut de « post », donc si vous voulez mettre en évidence un poste qui a été inscrit sur une page d'inscription, vous devrez utiliser. get_very_var () retourne juste une chaîne vide pour les types de poste qui ne sont pas personnalisés.

add_filter('nav_menu_css_class', 'current_type_nav_class', 10, 2 );
function current_type_nav_class($classes, $item) {
    $post_type = get_post_type();
    if ($item->attr_title != '' && $item->attr_title == $post_type) {
        array_push($classes, 'current-menu-item');
    };
    return $classes;
}

@Somatic - c'est fantastique! J'ai modifié votre code un peu si cela fonctionne aussi pour une taxonomie spécifique (que je me sers seulement pour les post_type connexes). L'idée est d'utiliser l'attribut de l'élément de menu Titre pour stocker à la fois le nom du post_type et le nom de la taxonomie, séparés par un point-virgule, puis explosé par la fonction.

add_filter('nav_menu_css_class', 'current_type_nav_class', 10, 2 );
function current_type_nav_class($classes, $item) {

    # get Query Vars
    $post_type = get_query_var('post_type');  
    $taxonomy = get_query_var('taxonomy');

    # get and parse Title attribute of Menu item
    $title = $item->attr_title; // menu item Title attribute, as post_type;taxonomy
    $title_array = explode(";", $title);
    $title_posttype = $title_array[0];
    $title_taxonomy = $title_array[1];

    # add class if needed
    if ($title != '' && ($title_posttype == $post_type || $title_taxonomy == $taxonomy)) {
        array_push($classes, 'current-menu-item');
    };
    return $classes;
}

Voici ma solution si vous voulez travailler avec wp_list_pages.

ajouter dans votre functions.php

add_filter('page_css_class', 'my_page_css_class', 10, 2);
function my_page_css_class($css_class, $page){
    $post_type = get_post_type();
    if($post_type != "page"){
        $parent_page = get_option('page_for_custom_post_type-'.$post_type);
        if($page->ID == $parent_page)
            $css_class[] = 'current_page_parent';
    }
    return $css_class;
}

Maintenant, il suffit d'ajouter dans la table wp_options une nouvelle ligne avec un option_name page_for_custom_post_type-xxxx et option_value page- ID u veulent se connecter.

Peut-être vous avez reconnu qu'il existe déjà une option appelée page_for_posts . Si u ont seulement 1 mesure le type de poste u peut définir votre page à /wp-admin/options-reading.php dans le menu déroulant et la navigation régler correctement le CURRENT_PAGE.

Je pense que noyau devrait étendre cette wordpress section avec un menu déroulant pour chaque type courrier recommandé.

J'ai décidé de coller avec des pages et utiliser le nom de modèle de page en tant que classe sur l'élément de navigation. Cela me permet d'éviter d'encombrer l'attribut de titre que je n'ai pas aimé quelques-unes des autres solutions.

add_filter('nav_menu_css_class', 'mbudm_add_page_type_to_menu', 10, 2 );
//If a menu item is a page then add the template name to it as a css class 
function mbudm_add_page_type_to_menu($classes, $item) {
    if($item->object == 'page'){
        $template_name = get_post_meta( $item->object_id, '_wp_page_template', true );
        $new_class =str_replace(".php","",$template_name);
        array_push($classes, $new_class);
        return $classes;
    }   
}

J'ai aussi des classes de corps ajoutés à header.php

<body <?php body_class(); ?>>

Enfin, cette solution nécessite une certaine supplémentaire pour appliquer css l'état sélectionné / actif à vos éléments de menu de navigation. Je l'utilise pour montrer les archives de taxonomie et les types de postes personnalisés liés à la page en tant qu'enfants de cette page:

/* selected states - include sub pages for anything related to products */
#nav-main li.current-menu-item a,
body.single-mbudm_product #nav-main li.lp_products a,
body.tax-mbudm_product_category #nav-main li.lp_products a,
#nav-main li.current_page_parent a{color:#c00;}

@Somatic - Grand code! Je l'ai fait faire un changement moi-même. Je voulais garder l'attribut Titre pour sa destination, de sorte qu'au lieu que je posai la limace de type post personnalisé dans les propriétés du menu avancées relationship Lien (XFN) que vous pouvez activer dans Options de l'écran. Je modifié

if ($item->attr_title != '' && $item->attr_title == $post_type) {

et modifié à

if ($item->xfn != '' && $item->xfn == $post_type) {

Nice travail Somatic.

Malheureusement, je ne reçois comment vous pouvez lister vos types de postes personnalisés dans une page la façon dont vous expliquer. Si je n'utilise une page portfolio.php et l'ajouter à une page, tous Tracez votre I est page 404.

Si je aime Gavin ne, je fonction que vous avez modifié un peu pour enlever aussi le « current_page_parent » de la page de blog comme celui-ci.

add_filter('nav_menu_css_class', 'current_type_nav_class', 10, 2);
function current_type_nav_class($css_class, $item) {
$post_type = get_query_var('post_type');

if (get_post_type()=='portfolio') {
    $current_value = "current_page_parent"; 
    $css_class = array_filter($css_class, function ($element) use ($current_value) { return ($element != $current_value); } );
}

if ($item->attr_title != '' && $item->attr_title == $post_type) {       
    array_push($css_class, 'current_page_parent');
};
return $css_class;

}

Licencié sous: CC-BY-SA avec attribution
Non affilié à wordpress.stackexchange
scroll top