Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Background Image with WebP fallback and data-src

So I am doing some optimisation work on my web site to improve Page Insights scores, two points that I can address are:-

  • Serve images in next-gen formats
  • Defer offscreen images

So images in next-gen formats, I have decided to use WebP but need to include fallbacks so they work in all browsers/devices.

Defer offscreen images; I am using data-src with a bit of JS script to set the background image as the data-src, the JS replaces the initial SRC which is src="data:image/png;base64,R0lGODlhAQABAAD/ACwAAAAAAQABAAACADs="

Taking the below as an example, how would I go about using inline background-image with WebP with fallbacks whilst deferring offscreen images?

HTML

<div id="working-bg" class="parallax" data-src="/wp-content/uploads/2016/08/silva-planning-parralax.jpg" style="background-image: url(/wp-content/uploads/2016/08/silva-planning-parralax.jpg)"></div>

JS for data-src

<script>
function init() {
    var imgDefer = document.getElementsByTagName('img');
    for (var i=0; i<imgDefer.length; i++) {
    if(imgDefer[i].getAttribute('data-src')) {
        imgDefer[i].setAttribute('src',imgDefer[i].getAttribute('data-src'));
    } }

    var imgDeferSpan = document.querySelectorAll('span[data-src]');
    var styleSpan = "background-image: url({url})";
    for (var i = 0; i < imgDeferSpan.length; i++) {
        imgDeferSpan[i].setAttribute('style', styleSpan.replace("{url}", imgDeferSpan[i].getAttribute('data-src')));
    }

    var imgDeferDiv = document.querySelectorAll('div[data-src]');
    var styleDiv = "background-image: url({url})";
    for (var i = 0; i < imgDeferDiv.length; i++) {
        imgDeferDiv[i].setAttribute('style', styleDiv.replace("{url}", imgDeferDiv[i].getAttribute('data-src')));
    }

}

window.onload = init;

</script>

Thanks in advance!

like image 615
nsilva Avatar asked Oct 24 '25 02:10

nsilva


2 Answers

Edit: Answer was incorrect, removed it

Checking on the backend for webp support where you serve the images should be the correct solution, and just redirect to the webp version if supported. Or do the same in JS, or another hacky solution can be, if you have nothing better is to load the img tag with the webp version, and onerror (<img onerror='loadJpg(this)/>) load the original version as a fallback, and make #bg.style.backgroundImage = img.src, it should update when the img.src changes

like image 156
Tamás Hájer Avatar answered Oct 26 '25 16:10

Tamás Hájer


Serve images in next-gen format: Use an image CDN like imagekit.io and get it done for you automatically. Most image CDNs have a free plan that's great for testing and small sites.

Defer offscreen images: Use a ready rolled solution like lozad.js that takes care of both images and background-images. For the background-image you can skip setting an initial inline style as the element has it's size set and will not cause any reflow when the image loads. For <img>s use an empty <svg> as the initial src value where 6 9 in the viewBox below defines the relation between width (6) and height (9) => change those values to fit your context.

data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 6 9'%3E%3C/svg%3E

Note that lozad.js uses Intersection Observer API that still lacks in browser support so be sure to add a polyfill.

Good luck!

like image 40
Peter Svegrup Avatar answered Oct 26 '25 15:10

Peter Svegrup



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!