Update: Marquex has written a plugin that takes care of all this without having to touch PHP. Check it out: Custom sidebar WordPress plugin
I’m going to show you (you, being the wordpress theme developer or modifier) how to add elements to your blog that will change based on which page you are on. A great example of this is changing which button is on for your navigation to indicate which section is currently active. I will also show you how to get multiple widgetized sidebars rocking for your theme. I’m going to make the assumption that you already know what wordpress pages are and how wordpress can act as a cms. I will also assume you know how to widgetize your theme. Onwards.
Creating multiple dynamic sidebars
Let’s take care of a simple task first, creating multiple sidebars. Normally for a standard wordpress theme you will have this function call to register your dynamic sidebar in your theme’s function.php file:
if ( function_exists('register_sidebar') ) register_sidebar();
That needs to go away. The code below allows you to create multiple sidebars and name each one uniquely. Just simply rename ‘sidebar#’ and put in as many sidebars as you like.
if ( function_exists('register_sidebar') ) { register_sidebar(array('name'=>'sidebar1')); register_sidebar(array('name'=>'sidebar2')); register_sidebar(array('name'=>'sidebar3')); }
Here is an example of wordpress 2.7.1 using multiple sidebars in the widget screen:
There is a catch with this. With multiple sidebars, most likely you are going to want to add the same widget to multiple sidebars. Some widgets allow you to have multiple instances of the widget on your sidebar(s). These widgets have a dropdown box in the admin section that allows you to select how many widgets you would like:
However, most do not. In this case you need to find the php code for the plugin that initializes the widget. You will be looking for the register_sidebar_widget call. For instance, in the delicious cached plugin, I found this function call:
register_sidebar_widget('Delicious Cached++', 'widget_deliciouspp');
All that you need to do is duplicate that line for as many widgets as you need and change the name in the first parameter. My php code now looks like this:
register_sidebar_widget('Delicious Cached++ 1', 'widget_deliciouspp'); register_sidebar_widget('Delicious Cached++ 2', 'widget_deliciouspp'); register_sidebar_widget('Delicious Cached++ 3', 'widget_deliciouspp'); register_sidebar_widget('Delicious Cached++ 4', 'widget_deliciouspp');
Now you should notice your admin interface show multiple instances of the widget like this:
Displaying different sidebars depending what page or subpage you are on
Now comes the fun part. Let’s get those sidebars showing up when you want them to. You’re going to want to add this code to your functions.php file. I won’t explain what it does until the next part (trust me) (also, thanks to Alberto for this post: http://www.altrugon.com/php/get-the-top-parent-page-in-wordpress/)
function getTopParentPostName($myid) { $mypage = get_page($myid); if ($mypage->post_parent == 0){ return $mypage->post_name; } else{ return getTopParentPostName($mypage->post_parent); } } function is_tree( $p_name ) { // $p_name = The page we're looking for pages underneath global $post; // We load this as we're outside of the post $top_post_name = getTopParentPostName($post); if ( $p_name == $top_post_name ) return true; else return false; }
Now, normally in order to register a dynamic sidebar for your theme, you just do this in sidebar.php (according to wordpress):
if ( function_exists('register_sidebar') ) register_sidebar();
You will be changing it to something like this where main page title # is your main page title name and sidebar# matches your sidebar names as discussed earlier:
if ( is_tree('main page title 1') ) { if (!function_exists('dynamic_sidebar') || !dynamic_sidebar( 'sidebar1') ) { $generic_sidebar = true; } } elseif ( is_tree('main page title 2')) { if (!function_exists('dynamic_sidebar') || !dynamic_sidebar( 'sidebar2') ) { $generic_sidebar = true; } } elseif ( is_tree('main page title 3' )) { if (!function_exists('dynamic_sidebar') || !dynamic_sidebar( 'sidebar3') ) { $generic_sidebar = true; } }
Here is what’s happening: the is_tree call checks to see if the current page or subpage you are on is in the family “main page title #”. If it is, then it registers the appropriate sidebar. That’s it! So, sidebars are cool and all, but what about other elements?
Displaying other elements depending what page or subpage you are on
This part is easy now that we’ve got the sidebars done. Let’s use an unordered list for top navigation as an example. I am just adding a class of “over” to the active menu item. You can see that the is_tree function is called again.
34 Comments
Is this your first step by step how-to post? You made it look easy… too easy… easy enough that I might actually try it.
Yeah, this is my first one. They’re quite fun to put together. It forced me to put the technicalities into words, something I don’t find easy to do.
Thanks!
Looking good bro.
Great how-to Eric! Also, the highlighting is gorgeous.
I am having problems getting this to work. I have copied everything you wrote but no sidebar shows, even though my template is widgetized and I added the code you mentioned.
Hi Tony,
So you’re not getting any sidebars to show up? What do you see when you go to the widgets link in the wordpress admin area?
Eric,
After I alter my functions.php file, I get an error that says
Warning: Cannot modify header information – headers already sent by (output started at /home/newhom5/public_html/wp-content/themes/arras-theme.1.3.5/arras-theme/functions.php:65) in /home/newhom5/public_html/wp-admin/theme-editor.php on line 70
any ideas?
Jayson,
From what I understand of that error it is most likely caused by extra spaces before or after your php tags. Try this article on wordpress.org that explains the problem.
Hopefully this helps, and sweet site, by the way.
I’ve experimented this problem (out of wordpress programming) and in my case the cause of the “extra spaces” in php files (which generate the error “Warning: Cannot modify header information – headers already sent by…” was my desktop code editor (Notepad++), who introduce sometimes the BOM byte at the top of the files for UTF-8 encoded files :S The “BOM byte” is like a non-ASCII character, so… because this reason it is INVISIBLE at the text editor when you open the file!! you only can detect it if you put the cursor just at the beginning of the file using Home key (keyboard) and then you move to the right with “right arrow key”… if the BOM byte exists at your file, then you will see that the cursor DON’T MOVE! 😉 only move with th second press of the “right arrow key”.
Well, incredible that it occurs!!! :S
SERGI
Eric – thanks for the getting back to me. I’ll check out the article right now.
when i use widgets, in other words, when i use functions.php file in theme directiory, some errors happen!!
like this:
Warning: Cannot modify header information – headers already sent by (output started at /home/javan/public_html/wp-content/themes/javan-club/functions.php:2) in /home/javan/public_html/wp-login.php on line 287
or this:
Warning: Cannot modify header information – headers already sent by (output started at /home/javan/public_html/wp-content/themes/javan-club/functions.php:2) in /home/javan/public_html/wp-includes/pluggable.php on line 689
can you help me?!plz!!
Hi Hosein,
What does your functions.php file look like, especially line 2? Normally this error is caused by code that is attempting to modify the header information of the page after some part of the body in the page has already been sent to the user. This could be as simple as a line break in your functions.php file. Most likely what is going on is functions.php has a line break in the code which would be outputted to the user. Then, any script modifying header information from that point on will cause the error.
Hope this helps. Feel free to report back your findings. I’m sure it will help others in the future.
This looks great. I am more interested in changing the body of my wordpress theme. I have a few games on my site that are much wider that the main column, but I eventually got that butchered enough it fits, but it doesn’t really look good. Any chances of a tutorial on something like that?
Thanks Tim for the question. I love being asked questions that could be turned into blog posts. I also do hourly work, btw 🙂
Got any advice for people using the Thisis theme by DIY Themes?
I have created the side bars but can’t use them yet because I don’t know where to put the code you referenced for sidebar.php
Does this part go in your functions or sidebar file?
if ( is_tree(‘main page title 1’) ) {
if (!function_exists(‘dynamic_sidebar’) || !dynamic_sidebar( ‘sidebar1’) ) { $generic_sidebar = true; }
}
elseif ( is_tree(‘main page title 2’)) {
if (!function_exists(‘dynamic_sidebar’) || !dynamic_sidebar( ‘sidebar2’) ) { $generic_sidebar = true; }
}
elseif ( is_tree(‘main page title 3’ )) {
if (!function_exists(‘dynamic_sidebar’) || !dynamic_sidebar( ‘sidebar3’) ) { $generic_sidebar = true; }
}
I have this line of code in my sidebar file, do I get rid of it?:
Also, I have different sidebars I want to show on different Pages. Where do I specify the Page name for each sidebar?
Thanks a ton.
Oops that line of code in my sidebar file was:
/* WordPress Widget Support */ if (function_exists(‘dynamic_sidebar’) and dynamic_sidebar(1)) { } else {
I am trying to do this with the wpng-calendar.php file from WPNG Calendar Plugin to have multiple widgets but I can’t seem to get it working once I duplicate the “register” line. Any help?
I’m sorry Nikhil, but I do not have any experience with the WPNG calendar plugin.
Thanks, could you tell me which plugin you used for the commenting on your site? I like it. Its clean and visual.
Thanks! I didn’t use a plugin, but used this tutorial for creating a base comments template and then edited it pretty heavily to make it work for this site.
This trick is awesome! I got it to work on all of my pages except for my blog page…any ideas?
Hello, thanks for the tutorial. I get my sidebars to show in the admin, but they don’t show on the pages. I’m new to wordpress so this may be a silly question… but does this method work with 2.8+?
Might want to add an else statement to the end of the code in the sidebar.php, so there is a default state, so you don’t have to program a custom sidebar for each and every page. This worked for me:
else {
if(!function_exists(‘dynamic_sidebar’) || !dynamic_sidebar() ) { $generic_sidebar = true; }
}
– ryan
The issue of getting different sidebars to appear on different pages is one that I have been looking for a solution to. Thanks!
Happy I could help!
Hey Eric, this is a great post first off. I wrote something similar, but this is much more versatile with the multiple instances of widgets, and coding, etc.
Anyways, I’ve gotten it to work nicely on a client’s site, but it does not seem to work when using a sub-sub page. The grandchild pages so-to-speak. Any idea why?
Is it possible to get a have a custom navigationbar depending on what page you are? Using wp-concept
Great post. I have to do something very similar to use different widgetized sidebars on the different sections of my site. As my understanding of WP and PHP grows, I’ve streamlined the code a bit but I wish there were a plugin to do this so I didn’t have such a big chunk of code on my page.php (I only use special sidebars on my pages).
There is a new wordpress plugin that allows to have multiple sidebars without writting any code, it’s called Custom Sidebars, and in few clicks you can create, widgetize, and set sidebars up.
http://wordpress.org/extend/plugins/custom-sidebars/
Cheers!
Thanks fo the info! I’ll check it out tonight and update this post if it works well.
so i just added the code into my theme.php and now my entire site wont work..when you click on the link to visit the page its just white
You Can also try this http://www.wordpressguide.in/want-different-sidebar-for-different-category.html
it is easy and simple !
Hi Eric
Thanks for mentioning the Delicious Cached++ plugin. I have recently refactored, and it now allows multiple widgets in a native (and more natural way). The “Delicious Cached++” widget appears only once, and you can add it multiple times (with independent settings – e.g., show bookmarks from different tags in each widget).
Let me know if you have more curiosity on how to allow multiple widgets in a WordPress plugin!
One Trackback