Default Image Captions in WordPress

I’m building a numismatic reference website in WordPress for the Perth Numismatic Society that is eventually going to list several thousand items along with images. The images will be presented as thumbnails which can be clicked on to show larger images using the Responsive Lightbox plugin. The client wanted a default caption under each image instructing users to click on the image to view a larger one. I honestly thought adding a default image caption would be easy but it turns out it isn’t. Nothing I Googled up actually worked including this example in the WordPress Codex or this plugin. So I actually had to use the old grey matter and work it out myself.

So I had a poke around the and ended up in the /wp-admin/includes/media.php file and found this function and filter:

function image_add_caption( $html, $id, $caption, $title, $align, $url, $size, $alt = '' )
{
//function code removed
}
add_filter( 'image_send_to_editor', 'image_add_caption', 20, 8 );

Ahah, simple. Remove the existing image_add_caption filter and replace it with my own. So, I’ve grabbed that code and added it and a couple of other things to my child theme functions.php file as:

remove_filter( 'image_send_to_editor', 'image_add_caption');
add_filter( 'image_send_to_editor', 'add_default_caption', 100, 8);
function add_default_caption( $html, $id, $caption, $title, $align, $url, $size, $alt = '' ) {

	/**
	 * Filter whether to disable captions.
	 *
	 * Prevents image captions from being appended to image HTML when inserted into the editor.
	 *
	 * @since 2.6.0
	 *
	 * @param bool $bool Whether to disable appending captions. Returning true to the filter
	 *                   will disable captions. Default empty string.
	 */
        if (substr($html,0,strlen('([0-9]+)/', $html, $matches ) )
		return $html;

	$width = $matches[1];

	$caption = str_replace( array("rn", "r"), "n", $caption);
	$caption = preg_replace_callback( '/<[a-zA-Z0-9]+(?: [^<>]+>)*/', '_cleanup_image_add_caption', $caption );
	// convert any remaining line breaks to <br>
	$caption = preg_replace( '/[ nt]*n[ t]*/', '<br />', $caption );

	$html = preg_replace( '/(class=["'][^'"]*)align(none|left|right|center)s?/', '$1', $html );
	if ( empty($align) )
		$align = 'none';

	$shcode = '' . $html . ' ' . $caption . '';

	/**
	 * Filter the image HTML markup including the caption shortcode.
	 *
	 * @since 2.6.0
	 *
	 * @param string $shcode The image HTML markup with caption shortcode.
	 * @param string $html   The image HTML markup.
	 */
	return apply_filters( 'image_add_caption_shortcode', $shcode, $html );
}

You can see I start by removing the existing image_add_caption filter but it turns out this is an utter waste of time because the filter executes even though I’ve removed it. So I’ve got around this by declaring the new filter with a lower priority than the existing one (so it happens AFTER) the existing filter. And then checked the $html to see if it starts with the caption shortcode. That’s this line:

if (substr($html,0,strlen('[caption'))=='[caption')
 return $html;

So, if a caption has already been applied we just exit from our new filter. ¬†However, if there’s no caption we can now apply our default caption like this:

if (empty($caption))
 $caption="Click Image to Enlarge";
This entry was posted in php, WordPress on by .

About markn

Mark is the owner and founder of Timesheets MTS Software, an mISV that develops and markets employee timesheet and time clock software. He's also a mechanical engineer, father of four, and a lifelong lover of gadgets.