KnpMenuBundle and dynamic route parameter

11,493

Solution 1

If your menu builder extends ContainerAware you should be able to access the request object. Example:

class Builder extends ContainerAware {
public function mainMenu(FactoryInterface $factory, array $options) {        

    $request = $this->container->get('request');        

    $menu = $factory->createItem('root');
    $parent = $menu->addChild('Users', array('route' => 'users'));
    $parent->addChild('Edit', array('route' => 'user_edit', 'routeParameters' => array('id' => $request->get('id'))));

    return $menu;
}

Your Users menu item should get the current_ancestor class

Solution 2

If your menu builder class does not extend ContainerAware (and, as a service, there's no need for it to do so) you can pass in the @request_stack, or typehinting Symfony\Component\HttpFoundation\RequestStack service, and fetch the id from there:

$id - $this->requestStack->getCurrentRequest()->get('id');
// -or- 
$request = $this->requestStack->getCurrentRequest();
$id = $request->get('id');
Share:
11,493
Chuck Norris
Author by

Chuck Norris

SOreadytohelp

Updated on July 22, 2022

Comments

  • Chuck Norris
    Chuck Norris almost 2 years

    i use knpmenubundle for my website and here is my problem : i've a list of user listed by this route : /admin/users and the menu is like this :

    User (is opened)
        list (is active)
        add new
    

    in the list view, the item "list" in the menu is active like i want in the add new view, the item "add new" in the menu is active like i want

    but, when i want to edit an user which allready exist, i can't manage to active the item "Users" because te route have a dynamic parameter

    here is how my site is structured :

    in src/dn/AdminBundle/Resources/Config/routing.yml

    # Users
    ### List
    dnAdmin_usersList:
        pattern: /users/{page}
        defaults: { _controller: dnAdminBundle:User:list, page: 1 }
        requirements:
            page:  \d*
    
    ### Edit
    dnAdmin_userEdit:
        pattern: /user/edit/{id}
        defaults: { _controller: dnAdminBundle:User:edit}
        requirements:
            id: \d+
    

    in app/ressources/view/layout/html/twig

    {{ render(controller("dnAdminBundle:Common:leftMenu")) }}
    

    in src/dn/AdminBundle/Controller/CommonController

    public function leftMenuAction()
    {
        return $this->render('dnAdminBundle:Common:leftMenu.html.twig');
    }
    

    in src/dn/AdminBundle/Resources/view/Common/leftMenu/html.twig

    {{ knp_menu_render('leftMenu', {'template':'dnAdminBundle:Menu:knp_menu.html.twig', 'currentClass':'active', 'ancestorClass':'active'}) }}
    

    in src/dn/AdminBundle/Resources/config/services.yml

    services:
        dn_admin.menu_builder:
            class: dn\AdminBundle\Menu\MenuBuilder
            arguments: ["@knp_menu.factory"]
    
        dn_admin.menu.leftMenu:
            class: Knp\Menu\MenuItem
            factory_service: dn_admin.menu_builder
            factory_method: createLeftMenu
            arguments: ["@request"]
            scope: request
            tags:
                - { name: knp_menu.menu, alias: leftMenu }
    

    in src/dn/AdminBundle/Menu/MenuBuilder.php namespace dn\AdminBundle\Menu;

    use Knp\Menu\FactoryInterface; use Symfony\Component\HttpFoundation\Request; class MenuBuilder { private $factory;

    /**
     * @param FactoryInterface $factory
     */
    public function __construct(FactoryInterface $factory)
    {
        $this->factory = $factory;
    }
    
    public function createLeftMenu(Request $request)
    {
        // root
        $menu = $this->factory->createItem('root');
        $menu->setChildrenAttributes(array('class' => 'sidebar-menu'));
    
        // Users
        $l = $menu->addChild('Users', array(
            'uri'    => '#',
        ));
        $l->setAttribute('class', 'treeview');
        $l->setChildrenAttribute('class', 'treeview-menu');
        $l->addChild('Liste', array(
            'route'  => 'dnAdmin_userList',
        ));
        $l->addChild('Edit', array(
            'route'           => 'dnAdmin_userEdit',
            'routeParameters' => $request->get('id'),
        ))
        ->setDisplay(false);
    }
    

    but $request->get('id') return empty string

    Anyone have idea on how i can get the current parameter in knpmenubundle?

    Thanks