Everything you need to know about the native lazy load
The lazyload feature allows developers to selectively control the lazyload attribute on <iframe>and <img> using the Feature-Policy header or the <iframe> “allow” attribute. This provides more control over loading delay for embedded contents and images on a per origin basis. Web developers can use this policy to force loading to delayed or non-delayed for your entire website and all or parts of any embedded contents. This will give a significant boost in page load times.
LazyLoad is a Chrome optimization that defers loading below-the-fold images and certain third-party iframes on the page until the user scrolls near them, which reduces data usage, speeds up page loads, and reduces memory use. For frames, third-party iframes that are meant to be shown to the user are deferred, leaving alone frames that are used for analytics or communication according to heuristics. For images, LazyLoad inserts placeholders with appropriate dimensions, which it gets by issuing a range request for the first few bytes of the image. When the user scrolls, deferred frames and images that will be visible soon start loading.
The resources Chrome consumes (e.g. users’ time, data, or phone memory) should be proportional to the user value it provides. For page loads, this means that Chrome shouldn’t waste any of these resources loading content the user will never see. For instance, pages often require scrolling to get to the bottom, and users don’t always scroll that far.
For foreground page loads, content that is not visible because it is below the fold should commence loading just in time to complete when scrolled to it.
The specific goal of this project is to greatly reduce the number of image and third-party iframe resources necessary to load a site by using visibility predictions to trigger their loading.
Key metrics of interest are network data, load latency performance and memory savings.
With the lazyload attribute, developers could prioritize the loading of different inline frames and images on a web page. This however could become a cumbersome process and not quite scalable for larger web sites specially given that applying the attribute is origin-agnostic. The lazyload policy aims to resolve this issue but changing a browser’s decision on enforcing lazyload attribute for a browsing context and its nested contexts.
A new policy-control feature for lazyloading will alter lazyload behavior for a browsing context and its nested contexts. The feature will potentially modify the behavior of user agent towards the lazyload attributed value for nested resources. Essentially, when the feature is disabled for an origin, then no resources inside the origin can escape lazyloading by setting lazyload=”off”. Specifically, if for a resource the lazyload attribute is set to:
- on: Browser should load the resource lazily.
- off: Browser ignores the attribute value and assumes auto.
- auto: There is no change in browser behavior.
This feature could be enforced either in the HTTP header or by using the allow attribute of an inline frame.
Using the feature
This feature can be introduced with the HTTP headers. For instance,
Feature Policy: lazyload 'src' https://example.com
would not allow synchronous loading for any <iframe> or <img> (that is not yet in the viewport) from origins other than’self’ or https://example.com.
Similarly, the feature could be set through the allow attribute of an inline frame:
<iframe src="https://example.com" lazyload="off" allow="lazyload 'none'"></iframe>
which disregards lazyload=’off’ for all the origins including the <iframe>‘s origin itself.
Which iframes should be deferred?
An iframe will be deferred if it satisfies all of the following:
- It’s a third-party iframe (i.e. a different origin than the embedding page),
- Larger than 4×4 in dimensions,
- Not marked as “display:none” nor “visibility:hidden”,
- Not positioned off-screen using negative x or y coordinates
LazyFrames defers frames by waiting to call FrameLoader::Load() until an installed IntersectionObserver fires when the user scrolls near the frame.
The LazyImages mechanism defers loading of images until the user scrolls near them. To preserve the layout and avoid reflow jank when loading images in, LazyImages inserts appropriately sized rectangular placeholders where the images will be, using the image placeholder mechanism that was created for the LoFi feature.
To achieve this, Chrome will issue range requests for just the first few bytes of images, and then attempt to extract the image dimensions from these chunks and display placeholders with the same dimensions in their place.
When Chrome determines that it should attempt to display a placeholder image, it should attempt to get the image in the following ways in order of precedence:
- If the full image is present and fresh in the cache, then use that.
- Otherwise, if the server supports range requests, and the image dimensions can be decoded from the first 2KB of the image, then generate and show an image placeholder with the same dimensions.
- Otherwise, fetch the entire full image from the server as usual.
If the original image is a progressive JPEG, and the first 2KB range of the image contains the full low-resolution version of the image, then Chrome will consider using that low-resolution version of the image as the placeholder.
Since there is a chance that LazyLoad could negatively affect user experience on some iframes and images, a per-element lazyload attribute will be provided for determining the policy for frames and images, to allow a page to optionally indicate to the browser if an iframe or image is well or poorly suited for lazy loading. By default, the browser will decide which frames and images on the page should be lazily loaded.
There will also be a way to control LazyLoad page-wide using feature policy.
At the time of writing LazyLoad is available in only available in Chrome Canary, behind two required flags:
Flags can be enabled by navigating to chrome://flags in a Chome browser.
- Public Proposal