Most WordPress themes show user Gravatars in the comment threads. It’s a way of showing an image with the user, as associated by the email address used. It’s a nice touch, and almost an expected design pattern these days.
Every one of those gravatars is an individual HTTP request though, like any other image. A comment thread with 50 comments means 50 HTTP requests, and they aren’t always particularly tiny files. Yeesh.
Let’s lazy load them.
In order to stop those HTTP requests for not-yet-seen images, we need to get our hands directly on the markup. If there is an <img src=""> in the HTML, there is essentially no way to stop the browser from downloading that image as soon as it possibly can, seen or unseen. So, we need to remove that src, and put it back when we’re ready.
It’s worth a pause here because we’ve entered some murky territory.
Altering the HTML
This is the change we’d be making:
<!-- Normal image. No beating the browser preloader. --> <img src="https://gravatar.whatever..." alt="" /> <!-- Let's change to this, which won't download anything. --> <img data-src="https://gravatar.whatever..." alt="" />
Although a missing src on the <img> is technically invalid HTML. It almost certainly doesn’t really matter in that it won’t affect how anything works. If the invalid HTML bugs, you could always toss a super minimal blank GIF data URL in there, like:
Using width and height attributes is probably a good idea too, to maintain layout and avoid reflow if and when the images to load.
Altering the HTML… in WordPress
But how do you change the HTML that WordPress spits out as part of a comment thread? Comments are slightly unusual in WordPress in that WordPress core gives you the HTML, it isn’t part of your theme like most of the other HTML is.
Likely, in your `comments.php` file, you’ll see this function:
<?php wp_list_comments(); ?>
Which spits out a pile of <li>‘s with your entire comment thread. Not a lot of opportunity there to be fiddling with the output of images. Except, we can! We can list a callback function in there:
Now We’re Ready to Lazyload
The hard part is over. We’re perfectly set up to do lazyloading now. If we were to write a script, it would be like:
Figure out the visible area of the browser window
Figure out the position on the page of every image with class .lazyload-gravatar
If any of those images are in the visible area, flop out the src with the value from data-src
If the visible area of the browser window changes in any way, re-evaluate the above
We could set about writing that ourselves. And we could do it! But, and I’m sure you’re not surprised here, it’s a bit tricky and nuanced. Cross-browser concerns, performance concerns, does-it-work-on-mobile concerns, to name a few. This is the kind of thing I’m happy to lean on other’s work for, rather than roll myself.
Again, no surprise, there are loads of options to pick from. In my case, I’m happily using jQuery on CSS-Tricks, and I picked a jQuery-based on that looked pretty good to me:
The API is as simple as can be. After bundled up the lib with the rest of the libs I’m using, I just call:
Look how nicely it works!
That’s an awful lot of saved HTTP requests and awful good for performance.
Makes you wish web standards and browsers would get together on this and make it a native feature.