Cómo codificar elementos de menú personalizados

22

¿Hay alguna forma de codificar los elementos del menú personalizado cuando se instala el primer tema? Estoy creando un tema que creará automáticamente algunas páginas comunes cuando esté instalado. ¿Entonces necesito saber si también puedo agregarlos al menú personalizado de Wordpress para que el cliente no necesite agregarlos manualmente?

En otras palabras: ¿cómo insertar / crear un elemento de menú personalizado mediante programación?

Avísame si algo no está claro. Guía de la página del códice correspondiente es bienvenida. ¡Gracias!


actualización: código probado desde aquí Orientación del menú específico con wp_nav_menu_items

Registro de menú:

function register_my_menus() {
  register_nav_menus(
    array('main-menu' => __( 'Main Menu' ) )
  );
}

add_action( 'init', 'register_my_menus' );

Uso de plantilla:

<?php wp_nav_menu( array( 'theme_location' => 'main-menu' ) ); ?>

Código para agregar nuevos elementos:

function new_nav_menu_items($items) {
    if( $args->theme_location == 'main-menu' ){
    $homelink = '<li class="home"><a href="' . home_url( '/' ) . '">' . __('Home') . '</a></li>';
    $items = $homelink . $items;
    return $items;
    }
}
add_filter( 'wp_nav_menu_items', 'new_nav_menu_items', 10, 2 );

Al agregar el código para agregar nuevos elementos en el menú de navegación en el functions.phparchivo, nada sucede en la página del menú en el panel de administración, pero los elementos del menú actual se han ido al sitio.

Sisir
fuente

Respuestas:

23

El problema con su código es que en realidad no está agregando los enlaces al menú y solo a la salida del menú, de ahí el uso de un filtro (add_filter) por lo que solo está filtrando la salida del menú, incluso si no lo hace tener un menú, su enlace se mostrará con el código que está utilizando. Pero para crear un enlace y agregarlo a un menú, puede usar este código:

$run_once = get_option('menu_check');
if (!$run_once){
    //give your menu a name
    $name = 'theme default menu';
    //create the menu
    $menu_id = wp_create_nav_menu($name);
    //then get the menu object by its name
    $menu = get_term_by( 'name', $name, 'nav_menu' );

    //then add the actuall link/ menu item and you do this for each item you want to add
    wp_update_nav_menu_item($menu->term_id, 0, array(
        'menu-item-title' =>  __('Home'),
        'menu-item-classes' => 'home',
        'menu-item-url' => home_url( '/' ), 
        'menu-item-status' => 'publish'));

    //then you set the wanted theme  location
    $locations = get_theme_mod('nav_menu_locations');
    $locations['main-menu'] = $menu->term_id;
    set_theme_mod( 'nav_menu_locations', $locations );

    // then update the menu_check option to make sure this code only runs once
    update_option('menu_check', true);
}

Comenté todo para hacerlo más simple.

Para crear un menú de página secundaria / subpágina / segundo nivel (como quiera que lo llames), solo necesitas configurarlo menu-item-parent-iden el nuevo elemento, por ejemplo:

//create the top level menu item (home)
$top_menu = wp_update_nav_menu_item($menu->term_id, 0, array( 
    'menu-item-title' =>  __('Home'),
    'menu-item-classes' => 'home',
    'menu-item-url' => home_url( '/' ), 
    'menu-item-status' => 'publish'
    'menu-item-parent-id' => 0,
    ));
//Sub menu item (first child)
$first_child = wp_update_nav_menu_item($menu->term_id, 0, array( 
    'menu-item-title' =>  __('First_Child'),
    'menu-item-classes' => 'home',
    'menu-item-url' => home_url( '/' ), 
    'menu-item-status' => 'publish'
    'menu-item-parent-id' => $top_menu,
    ));
//Sub Sub menu item (first child)
$Second_child = wp_update_nav_menu_item($menu->term_id, 0, array( 
    'menu-item-title' =>  __('Second_Child'),
    'menu-item-classes' => 'home',
    'menu-item-url' => home_url( '/' ), 
    'menu-item-status' => 'publish'
    'menu-item-parent-id' => $first_child,
    ));

También puede establecer la posición por código con menu-item-position y creo que se hace así:

  • Primer elemento - 'menu-item-position' => 1
    • Primer elemento primer elemento secundario - 'menu-item-position' => 1
    • Primer elemento segundo elemento secundario - 'menu-item-position' => 1
      • Primer elemento segundo hijo primer hijo - 'menu-item-position' => 1
  • Segundo elemento - 'menu-item-position' => 2
  • 3er elemento - 'menu-item-position' => 3
  • 4to elemento - 'menu-item-position' => 4
Bainternet
fuente
Esas son las funciones que estaba buscando :) codex no incluye estas :( Una pregunta más, ¿cómo puedo agregar un elemento secundario al elemento Home? Te lo haré saber tan pronto como llegue a mi PC. ¡Gracias!
Sisir
@Sisir: actualicé con un ejemplo cómo crear páginas secundarias
Bainternet
@Bainternet: recibí este error la primera vez que ejecuté el código Fatal error: Cannot use object of type stdClass as array in C:\wamp\www\citystir\wp-admin\menu.php on line 25. Pero el menú se crea y cuando la página se actualiza todo funciona, pero no se muestra nada en la Appearance -> Menu Theme Locationsección. Estamos muy cerca :) ¡Gracias!
Sisir
@Bainternet: Supongo que el código está obteniendo un error cuando intenta ejecutar el código $locations = get_theme_mod('nav_menu_locations');Entonces, los códigos anteriores (se realiza toda la inserción del menú) se ejecutan y el código posterior (establecer la ubicación del tema deseado) no se ejecuta .
Sisir
@Sisir: el código funciona bien, cuál es el nombre de la ubicación de tu tema y muéstrame el código exacto que estás usando, veré si puedo ayudarte.
Bainternet
8

Su código original está muy cerca del dinero y creo seriamente que esta solución larga de @Bainternet (sin ofender) es exagerada, así que eche un vistazo a esto:

function new_nav_menu_items($items, $args) {
    if( $args->theme_location == 'primary' ){
        $homelink = '<li class="home"><a href="' . home_url( '/' ) . '">' . __('Home') . '</a></li>';
        $items = $homelink . $items;
    }
    return $items;
}
add_filter( 'wp_nav_menu_items', 'new_nav_menu_items', 10, 2 );

Su único problema fue que no estaba devolviendo $ items después de que la función verificó el menú correcto, y le faltaba el segundo argumento de devolución de llamada que era necesario para hacer la verificación ( $ args ).

Foxinni
fuente
¿Cómo establecería la ubicación del elemento del menú utilizando este método?
Michael N
1

Hay un error en Wordpress 3.4.2:

https://github.com/WordPress/WordPress/commit/ae96b842f9f55ecfb22da705a4902b9d25580259#wp-includes/nav-menu.php

Necesita crear el término relación manualmente:

$menu = wp_get_nav_menu_object('top menu');
$id = wp_update_nav_menu_item($menu->term_id, 0, $data);

if ($menu->term_id && (!is_object_in_term($id, 'nav_menu', (int)$menu->term_id))) {
    wp_set_post_terms($id, array((int)$this->id), 'nav_menu');
}

Consulte https://gist.github.com/4148529 para ver un ejemplo de la clase Menú para la creación simple de menús.

OzzyCzech
fuente
0

Para obtener información, el usuario actual tiene derechos para agregar términos, mis elementos de menú se crearon pero no se agregaron en la tabla wp_terms_relationship antes de agregar una llamada a wp_set_current_user (1);

Grégocentrique
fuente