El andador de navegación personalizado muestra los elementos del menú actual, o hermanos, sin hijos

13

He estado buscando / buscando horas y aún no puedo hacer que esto funcione, por lo que finalmente estoy cediendo y pidiendo ayuda.

Estoy tratando de escribir un andador personalizado que muestre solo las páginas actuales de niños, o si no hay niños, muestre las páginas hermanos.

Por ejemplo, tome el siguiente árbol de menú:

  • 1.0
    • 1.2.0
      • 1.3.0
      • 1.3.1
      • 1.3.2
    • 1.2.1
    • 1.2.2
  • 2.0

Supongamos que estoy en la página actual 1.2.0. En esta página quiero mostrar sus hijos (1.3.0, 1.3.1, 1.3.2)

sin embargo, si estoy en la página 1.2.2, ya que no tiene hijos, debería mostrar su nivel actual de hermanos, por lo que debería mostrarme (1.2.0, 1.2.1, 1.2.2 ).

    
pregunta jchamb 27.01.2013 - 22:33

2 respuestas

4

Este es el caminante que solía mostrar solo para niños del elemento del menú actual. O los elementos del menú hermanos si no tiene hijos propios.

Hay comentarios en toda la clase que explican cada sección

<?php

class SH_Child_Only_Walker extends Walker_Nav_Menu {

private $ID;
private $depth;
private $classes = array();
private $child_count = 0;
private $have_current = false;


// Don't start the top level
function start_lvl(&$output, $depth=0, $args=array()) {

    if( 0 == $depth || $this->depth != $depth )
        return;

    parent::start_lvl($output, $depth,$args);
}

// Don't end the top level
function end_lvl(&$output, $depth=0, $args=array()) {
    if( 0 == $depth || $this->depth != $depth )
        return;

    parent::end_lvl($output, $depth,$args);
}

// Don't print top-level elements
function start_el(&$output, $item, $depth=0, $args=array()) {

    $is_current = in_array('current-menu-item', $this->classes);

    if( 0 == $depth || ! $is_current )
        return;

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

function end_el(&$output, $item, $depth=0, $args=array()) {
    if( 0 == $depth )
        return;

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

// Only follow down one branch
function display_element( $element, &$children_elements, $max_depth, $depth=0, $args, &$output ) {

    // Check if element is in the current tree to display
    $current_element_markers = array( 'current-menu-item', 'current-menu-parent', 'current-menu-ancestor' );
    $this->classes = array_intersect( $current_element_markers, $element->classes );

    // If element has a 'current' class, it is an ancestor of the current element
    $ancestor_of_current = !empty($this->classes);

    // check if the element is the actual page element we are on.
    $is_current = in_array('current-menu-item', $this->classes);

    // if it is the current element
    if($is_current) {

        // set the count / ID / and depth to use in the other functions.
        $this->child_count = ( isset($children_elements[$element->ID]) ) ? count($children_elements[$element->ID]) : 0;
        $this->ID = $element->ID;
        $this->depth = $depth;
        $this->have_current = true;

        if($this->child_count > 0) {

            // if there are children loop through them and display the kids.
            foreach( $children_elements[$element->ID] as $child ) {
                parent::display_element( $child, $children_elements, $max_depth, $depth, $args, $output );
            }

        } else {
            // no children so loop through kids of parent item.
            foreach( $children_elements[$element->menu_item_parent] as $child ) {
                parent::display_element( $child, $children_elements, $max_depth, $depth, $args, $output );
            }

        }
    }

    // if depth is zero and not in current tree go to the next element
    if ( 0 == $depth && !$ancestor_of_current)
        return;

    // if we aren't on the current element proceed as normal
    if(! $this->have_current )
        parent::display_element( $element, $children_elements, $max_depth, $depth, $args, $output );
}
}

Adjúntelo como lo haría con cualquier otro andador personalizado en un wp_nav_menu

<?php
wp_nav_menu( array(
    'menu' => 'primary-menu'
    ,'container' => 'nav'
    ,'container_class' => 'subpages'
    ,'depth' => 0
    ,'walker' => new SH_Child_Only_Walker()
 ));
?>
    
respondido por el jchamb 11.11.2013 - 22:20
0

Tuve una experiencia similar. Es posible que desee pensar en mover la lógica de las páginas fuera del caminante. Básicamente, compile la jerarquía de páginas actual como un objeto. Luego use el parámetro 'excluir' en la función wp_nav_menu. Ahora las páginas excluidas dependerían de si la página actual tiene hijos. Si no hay niños muestran hermanos; si hijos & & esos niños son el final de la línea muestran hermanos e hijos; si hijos & & y los nietos existen excluyen a los hermanos y muestran a los hijos y nietos.

    
respondido por el Steve Fischer 21.02.2013 - 13:01

Lea otras preguntas en las etiquetas