Lazy Loading - Plugins vs Own Script (where I'd need some help)

Ryuzaki

お前はもう死んでいる
Moderator
BuSo Pro
Digital Strategist
Joined
Sep 3, 2014
Messages
6,138
Likes
12,815
Degree
9
I'm considering using lazy loading since Google finally just released a new guide on how to make sure you do it in a way they can still crawl and index the images. The main thing they recommend in this secondary page is to use:
  • IntersectionObserver API
  • Polyfill for the API above for older browsers
All this API does is read when images are in the viewport or not. And you can set a padding so that when images are 200px, for example, away from being in the screen they go ahead and load so that you don't create jumps in the layout as they load random heights. It doesn't matter how you do this, it doesn't have to be the IntersectionObserver API. It can be something like jQuery.sonar too.

Pretty simple stuff. I then looked at some plugins to see how they were doing it. There's about 5 solid Lazy Load plugins and the rest seem shoddy. Of the main two, there's:
The first one uses jQuery.sonar and the plugin itself was made by Automattic (official Wordpress.com team), TechCrunch 2011 redesign team, and some guy called Jake Goldman. The second one was made by three guys I don't recognize. Both are being maintained it seems. This stuff doesn't break really unless Wordpress itself changes in some fundamental way.

My question is if you've used either of these plugins (recently is better) and are happy with them?

I like to avoid plugins where I can but will use one from a trusted team like Automattic who make money by keeping things updated.

Making one yourself is easy enough. You have to enqueue, for example, the IntersectionObserver API and Polyfill locally, then add an inline script in the footer or some other deferred javascript file you're already using. What this does is tell the main scripts (the API) to look for images with a certain CSS class attached like .lazy-load.

From there, it'll take the src="/path/to/image.jpg" and move it to a srcset= or data-src to hold temporarily. Then it populates the original src= with a placeholder image (which can be a 1x1 px image or some bigger one with your logo. When the image comes into view, it swaps the path to the image back to the src=.

From there you can apply CSS to make the images fade in or whatever you want.

You can make this source swapping and CSS class adding happen in the_content(); and then you can manually add the CSS class to your theme files if you want, like images in the footer.

So my next question is, in the case that the plugins above suck in some fashion, I need help with the Regex or whatever required to add a <noscript> catch for browsers and crawlers not using Javascript, because you'll need to go ahead and load the images instead of lazy loading them in that case. Could any of you help with that if the plugins suck? I'll share the main code minus that if that's the case.
 
I'm not that into WP development so can't help with its specifics, but just for inspiration I will share and interesting approach to pre-loading content in ReactJS.
Check the ReactJS's site. Basically when you hover a link, the content for that page gets pre-loaded and cached. That's the reason why that site is extra-snappy. Everything is cached by the point when you land on specific page.
Aq9jDqU.png
 
@GoldMarketing, that's cool. I've never thought about preloading like that. I do want to set up preloading for specific sitewide assets that don't otherwise get cached by my server and browser side caching. Thanks for sharing.
 
Did you decide on a way to go yet?

I have plenty of very image heavy content and Google insights hates me for loading them all at once.

The Lazy Load Plugin by Automattic seems to be the only credible plugin, but even with this one people seem to have trouble. Would love to do this with a simple script that won't be as likely to break stuff. I'd appreciate if you could update this thread if you find a solution.
 
The Lazy Load Plugin by Automattic seems to be the only credible plugin, but even with this one people seem to have trouble.

I think I'll be using this. I reviewed the code and it's very simple, so much so that I could yank it out into it's own function but what's the point. It's almost identical to the code I had found as well, except this plugin also includes the <noscript> I was worried about. It was just updated a few days ago too, so they're definitely staying on top of it.

The people having problems in the support forum seem like they are attributing other problems to this plugin as well as not knowing what they're doing in general. Like one guy saying the plugin added display: none; to every image and then didn't remove it when he uninstalled the plugin. That has nothing to do with this plugin at all. It's all done by replacing the image source, zero CSS involved.

I tested the plugin on a site of mine that is very image heavy that's just sitting right now. I'll let the domain expire when it's time to renew. It worked great.

The one thing to realize is that it filters images through the_content(); so it won't grab anything in the sidebars, footer, etc. If you want to do that, you have to either change the code manually in those sections, or there's some kind of filter that can be used but there's literally zero instructions on how to use it. I hate to manually change my theme to load a placeholder image, but it's not a huge ordeal. I'll likely do that to get the full benefit of lazy loading, especially if I can't figure out that extra filter they mention.

It seems safe and reliable, in my eyes, after reviewing all the files in the plugin.
 
With Wordpress sites, my best experience has been with the A3 Lazy Load plugin. It's simple to setup. It works with ACF, Woocommerce, video embeds, and also has a noscript fallback.

Using Fetch as Google, the screen shot that's rendered shows they are seeing lazy loaded images, at least on several of the sites I'm involved with. Using Google's Lighthouse audit tool (I prefer the CLI version, but the native Chrome tool works fine too), I also show no issues from the way the plugin loads. It's similar, as others have mentioned, in that it loads with a default image in the "src" field, original image in a "data-src" field, and swaps them out when it enters the viewport.

For other types of sites, and particularly static sites where you might want a simple solution, I've had the best results with the vanilla-lazyload script from Andrea Verlicchi. You'll like this, Ryuzaki, as it does use the Intersection Observer API. To get rolling, it's as simple as:
  • Add the script on page
  • Change image tags "src" attribute to "data-src"
  • Add the class "lazy" to your img tags
  • Add a script tag to create a new JS object for it
JavaScript:
var myLazyLoad = new LazyLoad({
    elements_selector: ".lazy"
});

That alone should get things working. You can improve on it though with different methods to handle placeholders, alternative sizes with data-srcset, and of course beefing up your script functions to add conditions, browser checks to load appropriately, etc. For reference, I use the UMD version of the script for simplicity sake.
 
Hey @Ryuzaki did you end up going with the Automattic plugin?

I did. It went exactly as I described above. It takes care of the_content(); automatically, and then you'll have to switch out the img src yourself for the data-src (I think that's what it was) and add the <noscript> if you're concerned with that.

Also, if you have any images stacked up, like in the sidebar, with no text between them, things will get funky unless you create a new placeholder image that's not 1x1 pixel but more like 1x100px so the height is included. The reason is that with 1px height and some images stacked, the API thinks the images should be lower down the screen. Like the 3rd image would be [300px + whatever margin you have times three] down the screen, but it's really now 3px down the screen. So you need to use different placeholder images in some spots.

Anyways, it worked out well and I'm happy and not looking back.
 
Back