Say I have a menu structure like this:

Parent1
- Child1.1
-- Grandchild 1.1.1
-- Grandchild 1.1.2
- Child1.2
-- Grandchild 1.2.1
-- Grandchild 1.2.2
- Child1.3
-- Grandchild 1.3.1
-- Grandchild 1.3.2

With Child1.1 as my active item, I wish to display the following menu block:

Parent1
- Child1.1
-- Grandchild 1.1.1
-- Grandchild 1.1.2
- Child1.2
- Child1.3

I.e. I want to see the parent, the siblings but restrict the children to the children of only the active item. Is there a way to achieve this at present, or could this option be added to menu_block?

Support from Acquia helps fund testing for Drupal Acquia logo

Comments

jstoller’s picture

I was just logging on to request this very same thing!

Currently, if the "Expanded" flag is checked for a menu item in the menu settings, then Menu Block will respect that and always expand that menu item. I would like to see an option in the Menu Block settings to "Only show children of active items." This would override the default behavior and, as the name suggests, only expand items along the menu's active trail.

My use-case is this... My primary navigation uses drop-down menus and I want to use the "Expanded" flag in the menu system to control which items are displayed in those drop-downs. However, I use Menu Block for my sidebar navigation, which I want to follow the active item and only show the children of that item. Currently, I am unable to both control the display of my drop-down menus and limit the expansion of my sidebar menu.

Tecktron’s picture

One more vote for this.

I set the active trail to follow my custom breadcrumbs (which works out great with custom nodes and views and well, a big mess really), but it in some cases, I want it to show my location's submenu in my menu block. An override (Show items children) in the block settings (without messing with the real menu settings as that screws up some other bits on the site) would be amazing.

Thanks!

skara’s picture

Version: 6.x-2.3 » 7.x-2.1

Would like to subscribe for this in 7.x

jstoller’s picture

Version: 7.x-2.1 » 6.x-2.4

This issue is requesting the feature in 6.x. I myself will be using Drupal 6 for quite some time and this feature is very important for me. Please post a separate issue for the Drupal 7 version rather than changing the version of this issue. Of course, if any headway is made on the 7.x version in this regard, I do hope it will be back-ported.

j.r’s picture

I also was wondering about this. I thought it could be easily configured because the side menu in the administrator section does this no?

Summit’s picture

Subscribing, greetings, Martijn

Kristen Pol’s picture

Subscribing... seems like this is the way pretty much anybody would want it to work.

Kristen

Kristen Pol’s picture

Since I need this to work right now, I added some code to my custom module. Perhaps this will help others. Note that this code is not done generically. The site I'm working on has a particular menu structure (same as the example noted in this issue) so I'm only handling that case. Also, I imagine the code could be more elegant but I'm not going to worry about that ;)

/**
 * In order to get menu items set as active when a page is not in the menu (via 
 * context), then we need to make sure to set the menu block to "expand all 
 * items" but this causes problems because then items that are not in the active 
 * trail are shown as well which is not desired. This function prunes out these 
 * children so only children of the active trail children are preserved. This 
 * function assumes that the menus are of the following form:
 *
 * [top-level]
 *   [2nd-level]
 *     [3rd-level]
 *   [2nd-level]
 *     [3rd-level] 
 *   [2nd-level] 
 *     [3rd-level] 
 */
function mycustommodule_menu_block_tree_alter(&$menu) {
  if (count($menu) == 1) {
    $menu_keys = array_keys($menu);
    $top_level_key = $menu_keys[0];
    $level_2 = $menu[$top_level_key]['below'];
    foreach ($level_2 as $menu_item_key => $menu_item) {
      $link = $menu_item['link'];
      if (! isset($link['in_active_trail']) || ! $link['in_active_trail']) {
        // get rid of children since they are not in the active trail
        unset($menu[$top_level_key]['below'][$menu_item_key]['below']);
      }
    }
  }
}   

Have fun!
Kristen

Kristen Pol’s picture

I got this working so now you can have it like:

[top-level] (this one shows up in menu block)
[2nd-level]
[3rd-level]
[2nd-level]
[3rd-level]
[2nd-level]
[3rd-level]
[top-level] (not showing up in menu block but is *in* the menu)
[2nd-level]
etc.

function mycustommodule_menu_block_tree_alter(&$menu) {
  // grab the top menu item from the active trail
  $top_level_key = NULL;
  foreach ($menu as $key => $menu_data) {
    if ($menu_data['link']['in_active_trail']) {
      $top_level_key = $key;
    }
  }
  if (! empty($top_level_key)) {
    $level_2 = $menu[$top_level_key]['below'];
    foreach ($level_2 as $menu_item_key => $menu_item) {
      $link = $menu_item['link'];
      if (! isset($link['in_active_trail']) || ! $link['in_active_trail']) {
        // get rid of children since they are not in the active trail
        unset($menu[$top_level_key]['below'][$menu_item_key]['below']);
      }
    }
  }
}
drupalchoice’s picture

Had the same issue with a D7 installation.
Created a menu block and then ticked the "Expand all children of this tree." checkbox.
But wanted only active parent to be expanded, not the sibling menu items.
My solution: use css to hide all chilldren then unhide the children of the active parent.
Worked like a charm, though I would have preferred a setting in the Menu Block module to achieve this.
CSS went something like this:

// first hide all children
.menu-block-wrapper li.expanded  ul.menu  {
	display:none;
}
// now unhide children of active parent
.menu-block-wrapper  .expanded.active-trail.active .menu  {
	display:block;
}
letzel’s picture

Amich, could you kindly explain to me where in which file you added your code snippet?

drupalchoice’s picture

Sorry for late reply just noticed - this is css - place as far down within your style.css file within your active theme.

Tom Ash’s picture

Hi Kristen,

How would you make your $level_2 variable $level_3? I suppose I should print_r($menu) but I'm not sure how I'd access the output of that from within a module, and hope'd you might know the answer off the top of your head :)

Thanks,
Tom

therealmfb’s picture

Hey guys,

I ran into this exact use case working on a client site myself and I swore that I had been able to get it working without using hook_menu_block_tree_alter. After a while of playing around, I think I figured it out.

Basically, in your menu block settings, if you choose 'Expand all children of this tree', it will do exactly that and show all children of the current menu tree, starting from whatever level you have specified. However, if you do not check that option, it will only show children of menu items which are marked as 'Expanded' in the menu system.

In my case, what I originally was getting was:

- Level 1
-- Level 2
--- Level 3 (only wanted this to show when you are on the page for Level 2 or the Level 3 page itself)

Once I figured it out, I went to the page to edit the Primary Links (or in your case whatever menu your menu block is pulling from), and set it so that only 'Level 1' was set as 'Expanded' in the menu system.

Now, as a result, when you are on any Level 1 page or Level 2 page without children, what you see is:

- Level 1
-- Level 2

But if you are on a Level 2 page that has menu children or the Level 3 pages themselves, it will pull them in because they are in the active trail, so you get the desired effect of:

- Level 1
-- Level 2
--- Level 3

TL;DR: I don't think you have to use hook_menu_block_tree_alter to show only children of active item. Simply uncheck the setting for 'expand all children of this tree' in your menu block and configure what links are set as 'expanded' correctly in your menu.

Hope this is helpful and isn't too confusing. I'll try to explain better if anyone has any questions.

Mark

jstoller’s picture

@therealmfb: The problem arises when you have different menus that you wish to behave in different ways. As I said in #1, my primary navigation uses drop-down menus and I want to use the "Expanded" flag in the menu system to control which items are displayed in those drop-downs. However, I use Menu Block for my sidebar navigation, which I want to follow the active item and only show the children of that item. Currently, I am unable to both control the display of my drop-down menus and limit the expansion of my sidebar menu. This feature, if implemented, would allow an individual menu block to completely ignore the "Expanded" flag.

therealmfb’s picture

@jstoller: Ah I see that your use case would prevent my proposed solution from working. Sorry for jumping the gun there. I agree that 'follow only the active trail' would be a cool addition that I'd be interested in seeing.

Tom Ash’s picture

As therealmfb points out, the 'expand all children of this tree' setting may be all some people are looking for - see e.g. http://drupal.stackexchange.com/questions/29887/menu-block-or-custom-men...

jstoller’s picture

@Thomas Ash, that may be true, but wanting one's drop-down menus and sidebar menus to behave differently does not seem like an unusual use case, so I think this issue is still very relevant.

macman’s picture

I'd like this to work like this, too. I think the problem with hiding them via css is that you will then have blank spaces.

yannickC’s picture

Version: 6.x-2.4 » 7.x-2.3
FileSize
1.62 KB

I wanted to do so also, so here is a patch that i made so that we can configure it to have the children of the active item only.

FMB’s picture

Version: 7.x-2.3 » 7.x-2.x-dev
Issue summary: View changes
FileSize
1.33 KB

Re-rolled against latest release.

FMB’s picture

Status: Active » Needs review
gmclelland’s picture

Status: Needs review » Needs work

@FMB - I think the patch needs some work. It didn't work for me.

In menu_block.admin.inc It is missing the variable_set in _menu_block_block_save()
variable_set("menu_block_{$delta}_paged", $edit['paged']);

In menu_block.module it is missing this line in function menu_block_get_config($delta = NULL) {
$config['paged'] = variable_get("menu_block_{$delta}_paged", $config['paged']);

In menu_block.admin.inc it is missing
variable_del("menu_block_{$delta}_paged");

In menu_block.install function menu_block_uninstall() it is missing
variable_del("menu_block_{$delta}_show_deepest");

Even after making the changes above, I couldn't get it to work.

FMB’s picture

gmclelland: you seem to understand the issues you're describing better than I do^^; (All I did was adapting the previous patch to the current version, at least I tried to). Could you provide a new patch?

FMB’s picture

The last patch worked until 2.4. This was an intent to re-reroll again against latest release, but don't take it into account.

FMB’s picture

mrfets’s picture

Strange behavior.
I have a multilingual drupal site (english/dutch).
I have configured the menu block and didn't turn on "expand all children"
The English version does show all the children whether I click te option or not.
The Dutch version however shows only the children of the active item....(like it's suppose to do)
It' s driving me nuts...

Any ideas ? Take a look at http://www.smans.com and play around with product & solutions and the language switcher...

Thanks in advance !

Coach S

jabbamonkey2’s picture

Does this patch show the following menu, when you are on either the Child1.1 or the Grandchild 1.1.1 page? (so, show the expanded grandchild menu, when on the active trail)?

Parent1
- Child1.1
-- Grandchild 1.1.1
-- Grandchild 1.1.2
- Child1.2
- Child1.3

FMB’s picture

jabbamonkey2: it's supposed to show immediate children, so when Parent1 is the active page, you'll get this menu:

Parent1
- Child1.1
- Child1.2
- Child1.3

And when Child1.1 (or Grandchild 1.1.1)G is active, this one:

Parent1
- Child1.1
-- Grandchild 1.1.1
-- Grandchild 1.1.2
- Child1.2
- Child1.3

Now, the patch would need to be re-rolled against the latest release...

jabbamonkey2’s picture

So when you say "rerolled against the latest release" ... then I wont be able to use the patch with the most recent? I'll need to wait for the next patch (if it's coming)?

FMB’s picture

jabbamonkey2: this is correct, a new patch is needed for the latest version. Sadly, I won't be able to work on it this week.

Claudia Sotto’s picture

Hey,

I'll follow this issue.

I'm having the same problem. In Drupal 7 this module works.
In Drupal 9 it doesn't show the children of the menu item.

My menu:
-item 1
--item 1.1
---item 1.1.1
----item 1.1.1.1
----item 1.1.1.2
---item 1.1.2
----item 1.1.2.1

In Drupal 7 is working:
Initial level: 3rd level (ex. item 1.1.1)
Fixed parent level: item 1
Maximal depth: 1
Follow the active menu item
First level will be children of active menu

I can see, when in term page 1.1.1, the menu:
-item 1.1.1.1
-item 1.1.1.2

In Drupal 9 I try (and it doesn't work)
Visibility initial level: 3 (ex. item 1.1.1)
Levels to be exibited: 1
Fixed parent level: Item 1
Follow the active menu item
Initial visibility level will be: sons of active menu level

- if I check "Expand all menu links", it shows all links at this menu level.
-item 1.1.1.1
-item 1.1.1.2
-item 1.1.2.1

- if i don't check "Expand all menu links", it shows nothing.