Додайте клас "has_children" до батьків li при зміні Walker_Nav_Menu


22

Я пишу персоналізований ходовий клас для wp_nav_menu і хочу, щоб можна було вказати, чи містить li підменю. Тому я хочу, щоб моя розмітка була такою:

<li class="has_children [other-wordpress-classes]">
    <a class="parent-link">Some item</a>
    <ul class="sub-menu">

Я знаю, як добре додати та видалити заняття, я просто не можу знайти що-небудь, щоб сказати мені, чи є у поточного елемента елементи для дітей.

Будь-які ідеї?

Заздалегідь спасибі.

Відповіді:


23

start_el()повинна отримати цю інформацію у своєму $argsпараметрі, але, здається, WordPress заповнює$args її лише якщо це масив , тоді як для користувацьких меню навігації це об'єкт. Про це повідомляється у квитку Trac . Але без проблем, ви можете заповнити це в собі, якщо ви також перекриєте display_element()метод у вашому користувальницькому ходунку (адже це найпростіше місце для доступу до дочірнього масиву елементів):

class WPSE16818_Walker extends Walker_Nav_Menu
{
    function display_element( $element, &$children_elements, $max_depth, $depth=0, $args, &$output )
    {
        $id_field = $this->db_fields['id'];
        if ( is_object( $args[0] ) ) {
            $args[0]->has_children = ! empty( $children_elements[$element->$id_field] );
        }
        return parent::display_element( $element, $children_elements, $max_depth, $depth, $args, $output );
    }

    function start_el( &$output, $item, $depth, $args ) {
        if ( $args->has_children ) {
            // ...
        }
    }

Привіт, Ян, Ви можете мені допомогти з цим питанням ? Я спробував ваш код, але я не міг змусити його працювати. Чи можете ви надати мені ще якийсь зразок коду?
Гірі

Дивіться повний приклад реалізації далі на цій сторінці.
rjb

Велике спасибі @Jan fabry .. Мене тримали за моїми власними ходунками. Напевно, ваш фрагмент мені допоміг.
Харіш Чінджу

7

Оновлення: Станом на WordPress 3.7 (жовтень 2013 р.) Додано класи CSS для позначення пунктів і сторінок дочірнього меню в меню тем - не потрібно використовувати користувальницьку прогулянкову систему, як про неї піклуються в ядрі WordPress.

Класи CSS названі menu-item-has-childrenта page_item_has_children.


Повне рішення для тих, хто поспішає (заслуговує на попередню відповідь Яна Фабрі), дивіться повну реалізацію нижче.

Виведіть навігацію в шаблон теми:

wp_nav_menu( array(
    'theme_location' => 'navigation-primary',
    'container' => false,
    'container_class' => '',
    'container_id' => '',
    'menu_class' => '',
    'menu_id' => '',
    'walker' => new Selective_Walker(),
    'depth' => 2
    )
);

Потім включіть у тему functions.php:

class Selective_Walker extends Walker_Nav_Menu {
    function display_element( $element, &$children_elements, $max_depth, $depth=0, $args, &$output ) {
        $id_field = $this->db_fields['id'];

        if ( is_object( $args[0] ) ) {
            $args[0]->has_children = !empty( $children_elements[$element->$id_field] );
        }

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

    function start_el( &$output, $item, $depth, $args ) {
        if ( $args->has_children ) {
            $item->classes[] = 'has_children';
        }

        parent::start_el(&$output, $item, $depth, $args);
    }
}

Отриманий HTML вихід буде нагадувати наступне:

<ul>
    <li><a href="#">Home</a></li>
    <li class="has_children"><a href="#">About</a>
        <ul class="sub-menu">
            <li><a href="#">Our Mission</a></li>
        </ul>
    </li>
    <li><a href="#">Services</a></li>
    <li class="has_children"><a href="#">Products</a>
        <ul class="sub-menu">
            <li><a href="#">Lorem Ipsum</a></li>
            <li><a href="#">Lorem Ipsum</a></li>                
        </ul>
    </li>
    <li><a href="#">Contact Us</a></li>
</ul>

Для отримання додаткової інформації про використання ходу WordPress класу див. Розуміння класу Walker .

Насолоджуйтесь!


Фатальна помилка: передачу посилань на час виклику було видалено в D: \ www \ wordpress \ wp-content \ themes \ wpt_theme \ функции.php на лінії 44
Тахір Ясін

Рядок № 44 є батьківським: start_el (& $ output, $ item, $ глибина, $ args);
Тахір Ясін

2

Ця функція - саме те, що ви хочете мати. Він також показує вам досить ефективний спосіб змінити елементи навігаційного меню. Крім того, ви можете відкрити його для більш досконалих (наприклад, дочірньої теми) функцій за допомогою фільтра елементів:

/**
 * Classes for a navigation named "Topnav" in the nav location "top".
 * Shows examples on how to modify the current nav menu item
 * 
 * @param (object) $items
 * @param (object) $menu
 * @param (object) $args
 */
function wpse16818_nav_menu_items( $items, $menu, $args )
{
    # >>>> start editing

    // examples for possible targets
    $target['name'] = 'Topnav';
    // The targeted menu item/s
    $target['items'] = array( (int) 6 );

    # <<<< stop editing

    // filter for child themes: "config_nav_menu_topnav"
    $target = apply_filters( 'config_nav_menu_'.strtolower( $target['name'] ), $target );

    // Abort if we're not with the named menu
    if ( $menu->name !== $target['name'] ) 
        return;

    foreach ( $items as $item )
    {
        // Check what $item contains
        echo '<pre>'; print_r($item); echo '</pre>';

        // First real world example:
        $item->classes = 'span-4';

        // Second real world example:
        // Append this class if we are in one of the targeted items
        if ( in_array( (int) $item->menu_order, $target['items'] ) )
            $item->classes .= ' last';
    }

    return $items;
}
add_filter( 'wp_get_nav_menu_items', 'wpse16818_nav_menu_items', 10, 3 );

І так, майже у кожному випадку немає потреби у користувальницьких ходунках.


Дякую, зараз мені потрібен ходунок, але я буду дивитись на це наступного разу!
патнц

1

якщо ви хочете зробити спадне меню, ви можете зробити це лише за допомогою css. зробити власні навички в WP з дітьми, WordPress автоматично призначає клас .sub-меню для дитини ul. Спробуйте цю CSS

    nav li {position:relative;}
   .sub-menu {display:none; position:absolute; width:300px;}
    nav ul li:hover ul {display:block;}

Ви можете додати jQuery, щоб трохи приправити його, але це повинно створити робоче спадне меню.


Дякую, це за багаторівневе меню, що розгортається, що я також вставляю елементи керування, але, безумовно, добре робити якомога більше з css!
patnz

-1
if ( $this->has_children ) {
    $item_output .= 'has_children';
}

3
Будь ласка, поясніть, що робить цей код і як він відповідає на питання.
cybmeta

І будь ласка, опублікуйте код у більш контекстному контексті. Як і у більшості людей, які відвідують, поняття не має, де спробувати це вставити, і помилиться.
s_ha_dum
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.