Here’s a step by step guide to adding a second menu area to a Twenty Twelve child theme. This menu will act the same as the default menu on mobile devices and display below the header area.
If you don’t know what a child theme is you can read more about it on the WordPress Codex or read my own article on how to Create a WordPress child theme
Prepare the child theme
- Create a Twenty Twelve Child theme or you can download a blank one Here (make sure to edit the top of the style.css file to reflect your own name and theme name)
- In the child theme folder, create a directory called “js” (without quotes)
- Copy from the Twenty Twelve folder, header.php and inside the js folder copy navigation.js
- Create a file called functions.php
- Upload functions.php to your child theme folder
- Upload header.php to your child theme folder
- Upload navigation.js to your child theme folder inside the js folder
Your child theme now contains the proper files and directory structure for the next part. Follow these template modifications for the files in your child theme folder.
Template modifications
Open functions.php and add this. This code dequeues the original Twenty Twelve navigation.js file and queues our ownIt also registers our second menu area.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
<?php // de-queue navigation js add_action('wp_print_scripts','tto_dequeue_navigation'); function tto_dequeue_navigation() { wp_dequeue_script( 'twentytwelve-navigation' ); } // load the new navigation js function tto_custom_scripts() { // Register the new navigation script wp_register_script( 'lowernav-script', get_stylesheet_directory_uri() . '/js/navigation.js', array(), '1.0', true ); // Enqueue the new navigation script wp_enqueue_script( 'lowernav-script' ); } add_action( 'wp_enqueue_scripts', 'tto_custom_scripts' ); // Add the new menu register_nav_menus( array( 'primary' => __( 'Top Menu (Above Header)', 'tto' ), 'secondary' => __( 'Lower Menu (Below Header))', 'tto'), ) ); ?> |
Save and close functions.php
Add the menu to the header
Open header.php and around line 48 find this line
|
1 |
</header><!-- #masthead --> |
Directly above that line add the following code. This adds a second menu call to the header.
|
1 2 3 4 5 6 |
<!-- Lower Navigation --> <nav id="lower-navigation" class="main-navigation" role="navigation"> <h3 class="menu-toggle"><?php _e( 'Lower Menu', 'twentytwelve' ); ?></h3> <div class="skip-link assistive-text"><a href="#content" title="<?php esc_attr_e( 'Skip to content', 'twentytwelve' ); ?>"><?php _e( 'Skip to content', 'twentytwelve' ); ?></a></div> <?php wp_nav_menu( array( 'theme_location' => 'secondary', 'menu_class' => 'nav-menu', 'fallback_cb' => false ) ); ?> </nav><!-- #lower-navigation --> |
You can change the name of the menu that appears on mobile by changing “Lower Menu” to whatever you prefer in this code.
We’re going to use the fallback_cb menu parameter so the new menu won’t list your pages in case you decide you don’t want to have it active. But remember, this will require you to create a new menu in Appearance > Menus and activate it before you’ll see the menu.
Save and close header.php
Add the javascript for mobile
Open /js/navigation.js, scroll to the very bottom and add the following code. We’re simply adding a copy of the current javascript but using a different ID #lower-navigation for the new menu. This will make the menu act the same as the default menu on mobile devices.
I’m not very good with javascript so there might be a better way to use a second ID for getElementById, if you know of one please let me know and I’ll update this.
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 |
// Lower Navigation ( function() { var button = document.getElementById( 'lower-navigation' ).getElementsByTagName( 'h3' )[0], menu = document.getElementById( 'lower-navigation' ).getElementsByTagName( 'ul' )[0]; if ( undefined === button ) return false; // Hide button if menu is missing or empty. if ( undefined === menu || ! menu.childNodes.length ) { button.style.display = 'none'; return false; } button.onclick = function() { if ( -1 == menu.className.indexOf( 'nav-menu' ) ) menu.className = 'nav-menu'; if ( -1 != button.className.indexOf( 'toggled-on' ) ) { button.className = button.className.replace( ' toggled-on', '' ); menu.className = menu.className.replace( ' toggled-on', '' ); } else { button.className += ' toggled-on'; menu.className += ' toggled-on'; } }; } )(); |
Save and close navigation.js and activate your new child theme. Now visit Appearance > menus, create a new menu and add it to the new lower menu area.
If everything went well you should see a second menu in your Twenty Twelve child theme. Be sure to resize the browser and test the menu.
Bonus
Some of you might want to only display the lower menu, but you can’t because Twenty Twelve displays your pages if there isn’t a menu active. Here’s how to do it.
Open header.php and find around line 42
|
1 |
<?php wp_nav_menu( array( 'theme_location' => 'primary', 'menu_class' => 'nav-menu' ) ); ?> |
Change it to
|
1 |
<?php wp_nav_menu( array( 'theme_location' => 'primary', 'menu_class' => 'nav-menu', 'fallback_cb' => false ) ); ?> |
Now visit Appearance > Menus and remove the menu from the top menu area and save. Adding the fallback_cb menu parameter prevents the menu from displaying your pages when there is no menu active.
If you want to remove the margin above the header and bring the header image closer to the top, you can add this to your CSS.
|
1 2 3 |
#site-navigation.main-navigation { margin-top: 0 ; } |
Enjoy your new menu and let me know how it worked out for you!
Hi, the menu works great except for the styling, using #lower-navigation .main-navigation to change the look but not working, any ideas?
Hi Chris, you can add the menu_id parameter to the menu call http://codex.wordpress.org/Function_Reference/wp_nav_menu then use that id to style it.
Thanks, that’s great. I’d like to make another menu and use it in a page with the other page content, is that possible?
Worked like a charm, thanks a ton!
Thank you very much for your article! Very useful and easy to understand.
Hallo – I gave you the url of my test-site – as you see there are two menus – the first one from top is my secondary menu. I tried both versions you suggested: the #lower-navigation id – css as suggested in style.css of my child-theme – did’nt function – then i tried out the menu-id parameter and again in the style.css of the child-theme didn’t function.
this style.css looks as:
/*
Theme Name: mytwentytwelve
Author: Peter Grab
Description: Child Theme von twentytwelve
Template: twentytwelve
*/
@import url(../twentytwelve/style.css);
#sec-menu .main-navigation ul.nav-menu, #sec-menu .main-navigation div.nav-menu > ul {
border-bottom: 0;
border-top: 0;
}
now i’m a complete novice to css in general and for wordpress in special – Could you please give me a tip?
the first menu – thats my secondary – should have no lines above and under it – it should be complete at the top border of the page and it should be written with smaller letters let me say 10px
You’re right, it’s not working properly with that CSS. I’ll need to look into this more.
You can use the ID alone to do what you need to though, be sure to add it to @media so it only affects the desktop menu and not th emobile menu.
thanks – this works! Now I can get rid of that META-widget.
Hi Zeaks
I’m confused: when should the @media be used with CSS and when doesn’t it matter, pls? I want to keep my modded Twenty Twelve child theme responsive, and am concerned that I might already have made changes to the style sheet, for example, that may be compromised the responsiveness. In other words, I guess, should the @media thingo be used every time a CSS change is made or CSS added to the style sheet? If not, when exactly, pls?
Cheers
Ross
Hi Rolanstein, unless you want to make changes to how your theme looks on mobile devices, you should always use @media. Here’s an example, lets say you want a red border around your navigation menu, if you added #access { border: 1px solid red; } then both the mobile menu and the regular menu would display the border.
If you added @media around it, then only the desktop version would show the border.
Twenty Twelve was designed for mobiles first, then using @media conditionals it was designed to work for desktop browsers.
Some things won’t matter such as, widget titles, post titles, comment areas, since they should look the same on both mobile and desktop. Anything for the layout, and menu I would use @media since they both display differently on mobile.
If you want to show me your changes you’ve made on a forum post or pastebin.com, I’ll let you know what you should add within @media tags
Very helpful and clear, Zeaks. Thanks a lot.
I will take you up on your kind offer. Makes sense to check whether I’ve messed anything up before continuing and applying your advice in the future. Haven’t used pastebin before, but let’s see how this embed goes:
Cheers
rolanstein
Hi Rolanstein, I had to removed your post, it was too long for comments, open a forum post if you need to paste a lot of code, it’s easier to read that way.
Your stylesheet looks good other than I would probably put the body .site { css within @media like this.
Images and everything else would apply to mobile view and desktop view, so it’s fine. If you notice something doesn’t look right on mobile, check to make sure you didn’t add css for the area without @media conditionals.
Whoops – sorry about that long section of code, Zeaks. I was intending initially to embed it using pastebin (this is what you’ve done with the section of my stylesheet you’ve just posted, I think?), but couldn’t work out how to do it! Duh…
Thanks, as ever, for your advice and willingness to assist. Will adjust the positioning of the body .site code as you suggest.
Hadn’t noticed your forums menu item. Will check them out.
Cheers!
rolanstein
Thanks for letting me know, I’ve noticed the forums have been quiet since I changed themes, I’ve added another link in the sidebar menu and I’ve added info on posting code to the comment form
Hi, I am a beginner on wordpress. I followed the changes proposed step by step. It worked perfectly when applied to the Child Theme, Thanks! I now have 2 Menus in my Appearance section. Is it possible to have only one of the Menus displayed on my pages. Example: Page 1 would have the Lower Menu and Page 2 would display the Standard Menu?
You can use body classes to hide the menu for certain pages or you can use an if statement to not display it for some pages.
Untested example:
This would hide it on page ID 703 and 2. the ! tells it if it isn’t page 703 or page 2, then display the menu.
To find the id of the page you can view the page in FireBug or visit admin > pages > all pages. Hover your mouse over the page and look at the URL, it should say something like this http://yoursite.com/wp-admin/post.php?post=703&action=edit and 703 would be the ID.