Multiple Category Post Slider for WordPress
Creating a slider that pulls posts from different categories has been a contested area for a while. I’ve always said that it can be heavy on the server, but if you have to resources feel free to try and pull it off. Well now here is a way to do it and save on server resources by using one of WordPress’ built in features to act as a cache.
First we need to decide on a slider. I have used Nivo Slider because it is the slider I’m most familiar with and it seems to be the most popular. Before we get on with the code, let’s take a look at what we are creating, I’m sure you all know by now that I’m a sucker for a pretty image.
Images used © Microsoft/Turn 10 (Forza Motorsport 4), NBC Studios (Chuck Season 5 Promotional), Warner Bros. Entertainment (Sucker Punch). Used for illustrative purposes only, no infringement intended (please don’t sue).
I’ve split the image to show how it could be used to feature a post from categories such as Games, TV, and Films respectively. You’ll have to trust me, but my test really did cycle through those images. I’ve only merged them using Photoshop.
Setting up Nivo slider is something I’ve gone over before, and because of that I’m not really going to go over it again, not wanting to repeat myself and all. If you need to know how to set things up, take a peek at my previous Nivo Slider tutorial.
Okay. Now we need to change the code a little. Let’s take a look at the HTML/PHP you should have for the slider at the minute:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
<div id="slider"> <?php $tmp = $wp_query; $wp_query = new WP_Query('posts_per_page=5&category_name=featured'); if(have_posts()) : while(have_posts()) : the_post(); ?> <a href="<?php the_permalink(); ?>"><?php the_post_thumbnail('nivothumb'); ?></a> <?php endwhile; endif; $wp_query = $tmp; ?> </div><!-- close #slider --> |
Now it works great, but we want to have posts come from different categories, and have a little bit of caching to stop the stress on the server. Let’s take a look at the altered code.
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 |
<div id="slider"> <?php $ttl = 6; // Hours till transient timout. $ttl = 60*60*$ttl; // Work out real timeout. $cats = array('games','tv','film'); $catPosts = get_transient('post_from_each_cat_slider'); if (!is_array($catPosts)) { $catPosts = array(); foreach($cats as $cat) { $tmpPosts = get_posts('numberposts=1&category_name='.$cat); foreach($tmpPosts as $tmpPost) { $catPosts[$tmpPost->ID] = $tmpPost; } } set_transient('post_from_each_cat_slider',$catPosts,$ttl); } if($catPosts) : foreach($catPosts as $post) : setup_postdata($post); <a href="<?php the_permalink(); ?>"><?php the_post_thumbnail('nivothumb'); ?></a> endforeach; endif; wp_reset_postdata(); wp_reset_query(); ?> </div><!-- close #slider --> |
Okay, I realize the code has changed a lot and you are probably thinking what was the point in having followed the Nivo tutorial? You also setup the code needed to work Nivo, plus this new code is built in place of the old code. Having the old code there worked sort of like a template. Anyway, let’s look at this new code.
First we set a variable called $ttl
this is short for ‘Time To Live’ and let’s us set the length of time our cache should last before refreshing. When the cache refreshes the visitor that causes that refresh will take a small performance hit so it’s up to you to balance the posts being up-to-date, the performance penalty on the server & the annoyance the slow down causes visitors. I find 4-8 hours to be a good area. The next line converts the hours to seconds for WordPress’ function later.
Now we set a variable called $cats
this contains an array of the category slugs we want to grab posts from. Pretty simple really. You can put as many categories as you like, but I advise keeping it below 6 as the more you add the more the performance hit will become noticeable, even with caching.
Next we set a variable called $catPosts
. This grabs the content of a WordPress transient. A transient is exactly like an option WP uses to store your Admin settings. However a transient dies after a pre-set interval. That makes it perfect for caching. So if the code has ran before this variable will hold all the post data from the last time it ran, if it hasn’t ran yet it will come bad empty letting us know to run the code to grab the post data.
This next part only runs should our transient return nothing/empty. We overwrite the $catPosts
variable to now be an empty array ready to take our posts. Now for each category we have we grab some posts using the get_posts
function and storing them in $tmpPosts
. This is used as this is a secondary loop & I think it’s a little neater (on this occasion) that using WP_Query. We then loop through the posts storing each one in the blank array we made earlier, using the ID of each post as the key in the array. Finally we set the transient. This must have the same name as the get_transient()
from earlier so if you changed the name please make sure to change this one too. We provide the array & the length of time it should live. It’s important to note that the array is auto serialized by the set_transient()
function when it is stored.
That is basically it. The rest of the code is a standard for each loop used with the output of get_posts()
. Note the use of setup_postdata()
to make sure all the normal functions output data from the correct post. Also note the use of the wp_reset_postdata()
and wp_reset_query()
. These reset the query & post data back to the original query so the rest of the page is unaffected by the custom loop. If you miss these out you may find strange problems occur with any loops/queries after this one.
That’s about it. I want to say a huge thank you to various sources around the web that I visited while trying to figure out how to create this code. I’m sure someone out there has done this already & probably done it better, but I just wanted to share how I did it and hopefully it will help someone out there before they lose their sanity trying to figure this out.
As always a big thank you for reading. If you need any hands on help with this or any of the tutorials here at Return True head on over to my Hire Me page, drop me an email & I’ll be happy to help out. If you just need a nudge in the right direction then drop a comment & I’ll try to help you the best I can.
2 Comments
Jen
Hi, I sent an email about this tutorial, but thought I would try my luck here. Is there a way to add other post data? Such as the title and post excerpt?
Paul Robinson
Hi Jen,
Sadly I didn’t get an email, could you resend it elaborating a little more on what it is you need & I’ll see if I can help you with this.