Back to all blogposts

The new native lazy loading for images and iframes in Chromium-based browsers

Tomasz Kajtoch

Tomasz Kajtoch

Senior Frontend Developer

In my previous article about lazy loading, we’ve learned that implementing it into a website requires using a third-party JavaScript library and modifying your application to be supported (or writing a custom solution yourself). Luckily, help is on its way – all this might change for the better thanks to a new proposal of native lazy loading that’s already available in the latest Chromium-based browsers! Let’s see what it has to offer. 

Check out my previous article on lazy loading if you haven’t already. Otherwise, let’s get to native lazy loading in Chromium-based browsers.

TL;DR?

Add a loading=”lazy” attribute to img or iframe tags that you want to load on demand. The browser will load these when users scroll near the element.

And here’s how it works:

Now, how did we get there?

Graphic assets are often the most significant part of the data required to display a page. Completely understandable from the UX/UI point of view though – they make your website look more appealing to the users. While these assets are needed, some of them may be off-screen. That makes it possible to defer loading them to the time when they are actually required – when a user scrolls down and is near seeing them. That operation of deferring loading resources is called lazy loading (or “on-demand” loading).

It’s always been quite tricky to implement lazy loading because of the need for writing additional JavaScript logic or using external libraries and modifying an application to support it.

Now we have a new option – a native implementation that just works and can be used easily by developers right at the time of adding new elements.

And by a fact that’s just an attribute, it can be used with every frontend framework. That’s something I’ve been waiting for.

Read more: A guide to Svelte – what can the rising frontend framework do for you?

Attribute specification

The full specification can be found in a proposal pull request on GitHub and I strongly encourage you to read the discussion there in order to see how it looks like to propose a new attribute to a living specification and what you need to think about. However, it’s not required to get to know how the loading attribute works, and we can just jump straight into values we have available:

  • lazy – flags asset as a good candidate to be loaded lazily,
  • eager – forces asset to load straight away disabling lazy-loading,
  • auto (or value not set) – leaves the decision to a browser.

What about scrolling?

Scroll distance threshold

All images and iframes above the fold (being visible without scrolling) load normally, others are loaded when the user scrolls near them. The distance when elements should begin loading is dynamic and depends on:

  • Connection type (e.g. 3g, 4g, unknown),
  • Type of resource (image or iframe),
  • Whether Lite Mode is enabled in Chrome for Android.

Currently, these values are hardcoded in Chromium’s source and can be overridden only using command line arguments. It may seem like a big issue of the native implementation but actually, it has one substantial advantage – it depends on the effective connection type of user’s device. It would require a lot of work to detect it correctly and we can assume that the values provided by authors of that feature are calculated correctly, so we don’t need to worry about it.

Note: Chrome 77 allows to experiment how different connection types are affecting distance threshold by setting network throttling in DevTools.

lazy loading meme loading symbol with caption they see me loadin they hatin

Lazy images

To make the native lazy loading work, you need to add a single attribute – loading="lazy" to an img element. However, you may want to prevent browser reflow when the image is loaded by adding dimensions to it (width and height attributes) or using styles.

Lazy iframes

iframe elements work slightly different than images. Chrome firstly checks whether the element is hidden (is/isn’t a good candidate to be lazily loaded). Chrome considers the element as hidden when:

  • the element’s width and height are 4px or smaller,
  • display: none; or visibility: hidden; is set,
  • the element is off-screen using negative positioning values.

 Iframes that aren’t labeled as hidden load when a user scrolls near them (like images).

Read more: JavaScript static site generators: let’s build a website from scratch!

What about the onload event?

Lazily loaded image and iframe element’s onload events are triggered – as you might expect – when data is completely loaded. So when the element is lazily loaded, onload fires as a user scrolls near it, and the data is fetched.

The document’s onload event works a little bit differently. Traditionally, the event has been fired when all images and iframes were already loaded. With lazy loading, the document doesn’t wait for deferred, off-screen elements to be loaded before triggering the event.

Lazy loading browser support

Currently, the native lazy loading feature has shipped with Chrome 76 stable release and is available in all Chrome 76+ based browsers. By the time of writing this article, I was able to use native lazy loading in Chrome, Opera, and Microsoft Edge Beta. There’s also an open implementation ticket for Firefox.

Feature detection

You can easily detect if native lazy loading is present by checking the loading property – it’s defined in prototypes of HTMLImageElement and HTMLIFrameElement: 

Examples of loading attribute

Here are some examples of using the new loading attribute that show how easy it is to actually use the feature.

What’s the future of native lazy loading?

Native Lazy Loading is a new proposal that might become a standard one day. Thankfully it’s been implemented in Chrome, and there are easy ways to polyfill it. I encourage you to play with the new loading attribute to get to know it. If you need full browser support, you might want to prepare a fallback to an old method using JavaScript. If you’re interested in that, I’ve already published an article about traditional lazy loading implementation in JS and React.

Read more: Code splitting with React & Webpack: advanced app optimisation

The Software House is promoting EU projects and driving innovation with the support of EU funds

What would you like to do?

    Your personal data will be processed in order to handle your question, and their administrator will be The Software House sp. z o.o. with its registered office in Gliwice. Other information regarding the processing of personal data, including information on your rights, can be found in our Privacy Policy.

    This site is protected by reCAPTCHA and the Google
    Privacy Policy and Terms of Service apply.

    We regard the TSH team as co-founders in our business. The entire team from The Software House has invested an incredible amount of time to truly understand our business, our users and their needs.

    Eyass Shakrah

    Co-Founder of Pet Media Group

    Thanks

    Thank you for your inquiry!

    We'll be back to you shortly to discuss your needs in more detail.