Custom size featured image thumbnail with fallback in WordPress

Occasionally you may need to display featured images in sizes other than WordPress’ default thumbnail, medium and large sizes. That’s quite easily solved with the add_image_size() and the_post_thumbnail() functions. Unfortunately, there are still 2 problems to be solved:

  • Some posts may not have images at all, or the author forgets to attach a featured image
  • Previous posts don’t have featured images

Here’s a solution that 1) resizes the featured image to the right size, 2) uses the first image in the post if a featured image is not set and 3) falls back to a default image if none of the above are true.

TimThumb

TimThumb is a popular script that crops and resizes images and then caches them that is used in many WordPress themes. Download the script from the project page and save it as timthumb.php in your wp-content folder.

The script’s purpose is to resize images that are not hosted on your website, and therefore unable to be resized by WordPress. By default it only resizes external images from a few ‘safe’ sources, e.g. flickr.com, but you can override that by setting define ('ALLOW_EXTERNAL', TRUE); in the script. Please read up on the TimThumb documentation.

Theme customization

functions.php

In your theme folder, add the following code to your functions.php file. If your theme doesn’t have a functions.php file, simply create it and save it into your theme folder.

add_image_size( 'featured-thumbnail', 95, 66, true );

// Figure out which image to be shown
function featured_image_thumb() {
	global $post, $posts;
	// If a featured image has been set, use the
	// featured-thumbnail size that was set above with the
	// class of 'optional_img_class'
	if (has_post_thumbnail() ) {
		the_post_thumbnail('featured-thumbnail',
		array('class' => 'optional_img_class') );
	}
	// If a featured image is not set, get the first image in
	// the post content
	else {
		$first_img = '';
		ob_start();
		ob_end_clean();
		$output = preg_match_all('/<img.+src=['"]([^'"]+)['"].*>/i', $post->post_content, $matches);
		$first_img = $matches [1] [0];

		// Define a default fallback image in case a featured image
		// is not set and there are no images in the post content
		if(empty($first_img)){
			$first_img = get_bloginfo("template_url").'/images/default.jpg';
		}

		// Generate the HTML code to display the image and resize
		// the image with timthumb.php
		return '<img class="optional_img_class" src=" . $first_img ." alt="" />';
	}
}

Code for grabbing the first image courtesy of WpRecipies.com: How to: Get the first image from the post and display it

In your theme

Call the featured_image_thumb() function in your theme, e.g.

<!--?php if ( have_posts() ) : while ( have_posts() ) : the_post(); ?-->
	<a class="&quot;featured-image&quot;" href="&quot;<?php">" title="<!--?php the_title_attribute(); ?-->">
		<!--?php echo featured_image_thumb(); ?-->
	</a>
<!--?php endwhile; endif; ?-->

Don’t forget to regenerate your previously uploaded images

The add_image_size() function only works on images that are uploaded from this point forward. You can force WordPress to regenerate the images again with that specific size by using the Regenerate Thumbnails plugin.


23 Comments on "Custom size featured image thumbnail with fallback in WordPress"

  • Dani says

    Hi, this sounds great and pretty much what i was looking for. i was wondering if it would be possible that in case no featured picture is set, to use the first (or any random) picture uploaded into a (standard) gallery of a post? or is there no difference? (because i actually never place pictures into a post, only galleries). The thing is that i have a template called gallery, where i simply want to put all posts (in my case nothing more then photo albums, no text). So i am looking for a way how to post only the featured image (ore only one) of a gallery. Your post is interesting, because it would assure that there would be always a featured image, even if i forget to set one. Do you understand how i mean this? Thanks a lot! Great post and super smart idea!

    • blogjunkie says

      Hi Dani, if you want to get images in the gallery you’ll need to use the get_children function. You can adapt the code from this post to achieve what you need:

      http://johnford.is/programmatically-pull-attachments-from-wordpress-posts/

      If you need more help please email me directly – david at theclickstarter dot com

      • Dani says

        It is amazing! First of all i realised i didn’t came back to you to say thank you so much! Your hint and the link to john ford was exactly the key to my problems. i was now wondering, if there is also the possibility to automatically use the last added picture as featured image instead of the first added picture. i certainly could do it manually, but the whole idea was to have it done automatically… any idea?

        • blogjunkie says

          Hi Dani, I haven’t used this before myself, but PHP has a function to get the last item in an array: http://php.net/manual/en/function.end.php

          Perhaps you can use it to grab the last image from $matches. Let me know how it goes!

          • Dani says

            Hey, Thanks a lot for the hint, i will try if i can figure it out. its amazing how much you know, i mean, even if you don’t know, you know where to look. thanks a lot!

    • Hey man, great stuff and this is exactly what I needed, however there was just one thing I was hoping you help me with with the code.

      Is there a way to axe the function that pulls the featured image from the post and just have the function either pull the first image and resize or use a default image?

  • I had a cobbled together script to work with TimThumb for automatically pulling the thumbnail for the first image or featured image, but this is written much cleaner and easier to setup. Nice work, and thanks for sharing.

    Only one question, I have simply duplicated the function with a different name in order to provide different sized thumbnails for the Index, and Archive pages (230xx129px and 325pxx183px). Is there the possibility of cleaning up the script to handle multiple image sizes?

    I am not a programmer so it is beyond my knowledge, and your help already has been very appreciated.

    • blogjunkie says

      Hi Jody, the easiest way would be to duplicate the function and rename it to archive_image_thumb() so that you can have 2 different sizes. I’ll try to improve the script further in a future post 🙂

  • hi, this is a nice solution but how do you create a real fall back thumbnail?
    with the given solution a post thumbnail is shown in the frontend but it’s not registrated as a real post thumbnail in the backend in the backend.

    any real solution?
    best regards
    thomas

    • blogjunkie says

      Hi Thomas, I don’t think what you’re looking for is possible. What if the post doesn’t have any images attached? Or what if the image is hot linked from an external site?

      Maybe this could be an acceptable alternative – http://wordpress.org/extend/plugins/default-post-thumbnails/

      • hey blogjunkie,
        the default-post-plugin was exactly what i was looking for!

        many many thanks!!!!!!!!!!

        • but hey this plugin only works until 2-9-1
          so it’s broken for the latest wordpress version :-((

  • Just copied/pasted your code (forgot to say thank you!) into a test template here: freeseostuff.com (stay tuned I’ll lunch it SOON!) anyway, it gives me this error (if I activate wp-debug): Notice: Undefined offset: 0 in …./functions.php on line 505

    on line 505 I have:
    $output = preg_match_all('//i', $post->post_content, $matches);

    any idea about how to solve it?

    • blogjunkie says

      Hmm.. so if you turn off wp-debug there’s no error?

      Not sure what it means because my code above has nothing about an offset. Maybe it’s caused by code before line 505?

      Sorry I can’t be more help than that.

  • Best function script ever!

    You saved my butt, and your comments made it easy to customize the code and remove the part that calls the featured image 🙂

    • david says

      You’re welcome!

      • Hi David,

        After implementing this, I noticed the images do not display in firefox or internet explorer. I think I may have missed something.

        • david says

          Sorry mate, but I can’t provide support for the code above here. My advice would be to look in the source of the page to see if the HTML is being output wrongly – it might be a typo in your code. If you need help, I suggest asking on wordpress.stackexchange.com. Good luck

          • I figured it out. I removed this portion of the original code to stop it from pulling the featured image:

            if (has_post_thumbnail() ) {
            the_post_thumbnail(‘featured-thumbnail’,
            array(‘class’ => ‘optional_img_class’) );
            }
            // If a featured image is not set, get the first image in
            // the post content
            else {

            For some reason that make the thumbnails disappear in IE and firefox.

            Is there a way to keep it from pulling the featured image, but still pull the first and use the default?

          • Aw, found the solution and it’s completely unrelated to your magnificent code.

            Just in case anyone else has the same issue, uncheck “filter suspicious query strings” under WP Better Security if you’re rolling with it, and the thumbnails should show up in firefox and IE.

          • david says

            That’s great to know and thanks for sharing the solution 🙂

Leave a Reply

%d bloggers like this: