WordPress, Google PageSpeed Insights and WebP Image Formats

If you evaluate your website using Google PageSpeed Insights, you may find it complaining that you’re not using the WebP image format.

First Scan

The first scan with PageSpeed Insights gave me pretty good results for desktop, and somewhat poor results for mobile. The highest rated opportunity promised to save seven seconds in load time. I find that a bit doubtful, along with a number of other assessments by Google’s automated tool that seemed to ignore Google’s own scripts. While I was suspicious of the weighting of these issues, it is always a good idea to reduce load time and data consumption for users whenever possible.

Google PageInsights Opportunities relating to the webp image format

WordPress Plugins

There are a number of WordPress plugins that provide this functionality. The top currently listed on in the WordPress plugin directory are Imagify, WebP Express and WebP Converter For Media. I didn’t evaluate any of these solutions, instead wanted to see if I could develop a custom solution.

WordPress Filter

I wanted to see what was involved with developing a custom solution. I wanted something that could easily replace the existing thumbnails that I had in the layout, and ideally use core WordPress functions.

GD WebP Function

I started by creating a basic test to generate a WebP file from a PNG using the GD image library. The imagewebp function was able to create a WebP file as easily as a JPEG or PNG. The support for the format seemed pretty solid. After adjusting folder permissions, I was able to read a JPEG and write the WebP file.


Thumbnail Filter

I wanted to use filters, if at all possible. While sometimes StackOverflow can yield a quick result, the WordPress developer documentation is usually very helpful. I wanted to find a suitable filter that was executed before the HTML output but ended up using the HTML filter instead. In order to extract the img src, I used a regular expression. And I stored all the WebP images in a webp folder within the uploads folder.

/**
 * Filter to add webp version to thumbnail output
 *
 * @param string $thumbnail_img
 * @return string
 */
function filter_image_thumbnail_webp( $thumbnail_img ) {
	preg_match('/< *img[^>]*src *= *["\']?([^"\']*)/i', $thumbnail_img, $img_src_matches);
	$thumbnail_src = $img_src_matches[1];
	$thumbnail_src_parts = explode('/', $thumbnail_src);

	$dest_file = $thumbnail_src_parts[count($thumbnail_src_parts) - 1];
	if (stristr($thumbnail_src, '.png')) {
		$dest_file = str_replace('.png', '.webp', $dest_file);
		$img_type = 'image/png';
	} else {
		$dest_file = str_replace('.jpg', '.webp', $dest_file);
		$img_type = 'image/jpeg';
	}
	$upload_dir = wp_upload_dir();

	$dest_src = $upload_dir['baseurl']  . '/webp/' . $dest_file;
	$dest_file = $upload_dir['basedir']  . '/webp/' . $dest_file;

	if (!file_exists($dest_file) && file_exists($thumbnail_src)) {
        if ($img_type === 'image/png') {
            $im = imagecreatefrompng($thumbnail_src);
        } else {
            $im = imagecreatefromjpeg($thumbnail_src);
		}
		
		imagewebp($im, $dest_file);
		imagedestroy($im);
	}

	$output = '<picture>
		<source srcset="' . $dest_src . '" type="image/webp">
		<source srcset="' . $thumbnail_src . '" type="' . $img_type . '">'
		. $thumbnail_img 
		. '</picture>';

    return $output;
}
add_filter( 'post_thumbnail_html', 'filter_image_thumbnail_webp' );

Template Output

The goal was to keep this as simple as possible.

<?php the_post_thumbnail(); ?>

Second Scan

The results from Google PageSpeed Insights were better the second time. The score went up a few points for both mobile and desktop, and the issue was resolved.

In Conclusion

While I appreciate the progress that has been made with various file formats over the years, it is important that any format become almost ubiquitous. Part of the problem is that WebP isn’t very commonly known, and not universally supported in graphics applications. I doubt we’ll see WebP become an everyday format but optimized images and formats could very well grow in popularity. Regardless, it helps to pass generating the WebP files to a widely used plugin or library, or a custom solution like the filter I created.