By default, Drupal allows you to set a “primary” menu and a “secondary” menu. At this point you should know that if you go to admin-> menus -> settings and pick the same menu for both primary and secondary links, the secondary links menu will contain the sub-menu of the selected item in the primary menu.
What happens if you have three levels of menus?
Problem: the lack of a tertiary menu
What happens if you have three levels of menus? For example, what happens if your menu looks like this:
- One
- One one
- —One one A
- —One one B
- —One one C
- One two
- —One two A
- —One two B
- One three
- —One three A
- —One three B
- Two
- Two one
- —Two one A
- —Two one B
…ecc.?
PHPTemplate will create a two nice variables for you, $primary_links and secondary_links. Also, $secondary_links will contain the “right” entries if you set the primary menu and the secondary menu the same. What about $tertiary_links? Nowhere to be seen.
Searching for a solution
If you search the forums about this topic, you will find the most diverse solutions. They all take considerable efforts.
The first question you want to ask is: how does the template generate those links?
If you look at themes/engines/phptemplate/phptemplate.engine, and look for the string primary_links, you will find:
'primary_links' => menu_primary_links(), ... 'secondary_links' => menu_secondary_links(),
If you search Drupal’s codebase for those functions:
# grep -il menu_primary_links `find .` ./includes/menu.inc ./themes/chameleon/chameleon.theme ./themes/engines/phptemplate/phptemplate.engine ./themes/engines/phptemplate/.svn/text-base/phptemplate.engine.svn-base #
Ah! Menu.inc seems to be the way to go. The first function you find is:
/**
* Returns an array containing the primary links.
* Can optionally descend from the root of the Primary links menu towards the
* current node for a specified number of levels and return that submenu.
* Used to generate a primary/secondary menu from different levels of one menu.
[...]
function menu_primary_links($start_level = 1, $pid = 0) {
This is probably a little complex for a non-programmer.
However, menu_secondary_links() really gives everything away:
/**
* Returns an array containing the secondary links.
* Secondary links can be either a second level of the Primary links
* menu or generated from their own menu.
*/
function menu_secondary_links() {
$msm = variable_get('menu_secondary_menu', 0);
if ($msm == 0) {
return NULL;
}
if ($msm == variable_get('menu_primary_menu', 0)) {
return menu_primary_links(2, $msm);
}
return menu_primary_links(1, $msm);
}
The second if is obviously checking if primary and secondary links come from the same menu. If they are, then it just prints them out.
So, you can assume that this:
menu_primary_links(3, variable_get('menu_primary_menu', 0) );
Will return the “tertiary” menu!
The last piece of the puzzle is the rendering. FOr that, just see what any theme does:
<?php print theme('links', $primary_links, array('class' => 'links primary-links')) ?>
The solution
At this point, the solution should be clear. Just type:
$m=menu_primary_links(3, variable_get('menu_primary_menu', 0) );
print theme('links', $m, array('class' => 'links tertiary-links'));
Anywhere, and you will get your “tertiary links”! You can place this code in a block, or in the template directly.
Troubleshooting
- Make sure that the secondary menus are “expanded”
- Make sure you have <?php and ?> around the code
Best voted contents
-
Free software heroes: from Stallman to Google, a list of inspiring individuals who made everything possible
Tony Mobily, 2008-06-15 -
Ian Lynch's take on the BECTA fiasco
Tony Mobily, 2008-06-17 -
The Groklaw effect hits Becta. And yes, I am coining a new term
Tony Mobily, 2008-06-15 -
Mail merge in OpenOffice.org
Michael Crider, 2008-06-17
Buzz authors
All news
Other sites
- The Top 10 Everything (Dave). The good, the bad and the ugly.
- Free Software news (Dave & Bridget). All about free software -- free as in freedom!
- Book Reviews: Illiterarty (Bridget). Book reviews, blogs, and short stories.
Hot topics - last 60 days
-
A future without Microsoft
Tony Mobily, 2008-06-08 -
Free software heroes: from Stallman to Google, a list of inspiring individuals who made everything possible
Tony Mobily, 2008-06-15 -
Vienna failed to migrate to GNU/Linux: why?
Tony Mobily, 2008-06-09 -
Dubious ads in Free Software Magazine
Tony Mobily, 2008-05-25 -
The Bizarre Cathedral - 6
Ryan Cartwright, 2008-05-25
Hot topics - last 21 days
-
Free software heroes: from Stallman to Google, a list of inspiring individuals who made everything possible
Tony Mobily, 2008-06-15 -
The Groklaw effect hits Becta. And yes, I am coining a new term
Tony Mobily, 2008-06-15 -
Is Asus backsliding on GNU/Linux?
Gary Richmond, 2008-06-19 -
Charging for GNU/Linux is not the answer
Ryan Cartwright, 2008-06-15

Dedicated server
Drupal 6
Submitted by xiffy on Tue, 2008-06-17 13:37.
Vote!Thanks for the clear explanation. Unfortunatly, every new drupal version needs revision of almost any hacks. No exception for this one.
To get the tertiary links in Drupal 6 you would do
$m = menu_navigation_links(variable_get('menu_primary_links_source', 'primary-links'), 2);
because menu_primay_links() has lost it's footprint in Drupal 6
hth