DEV Community

Paul (hxii) Glushak
Paul (hxii) Glushak

Posted on • Originally published at 0xff.nu

Image Optimization for The Web

In my previous rant about web bloat I briefly spoke about image sizes and incorrect image usage and what you can do to either reduce it or make your visitors' life easier.
A specific toot prompted me to continue and expand about this with the hopes that this information will help some of you.

TL;DR

Images, like anything else, are to be use to answer a need or solve a problem1 (like demonstrating something in a visual manner).

If you don't absolutely need images - don't use them. If you have to use images, make sure they are optimized.

Image Formats

Many things have been said about image formats and I will most likely have nothing new to contribute, so instead I'll direct you to some useful reading material:

Image Size

Before I delve into fancy (and helpful) tricks that you can do to make sure your page load speeds are not inhibited by images, it is important to deal with the root of the problem - image size.

As I mentioned in my previous rant (linked above), I often see websites usings images of disproportional sizes (both image dimension and filesize) to their intended purpose where people would, for example, use a large (1728x1152) profile photo and resize it via CSS (to 30%, effectively 496x331 on a 1080P display):
Very large profile photo

I'm not going to rant (again) why you really (really) shouldn't do this, so we'll get straight to it.

Optimize. Optimize your images. Deal with the dimensions first - if you know you're only going to use 30% of your image, resize it beforehand!
Using smaller dimensions will also result in smaller filesizes.

You think larger screens deserve larger images (not of your fucking face, please!)? Save multiple sizes and use srcset.

You made your images smaller? Thank you! You want to go the extra mile? Use optimization tools, either online or offile. For example:

Online Tools

Offline Tools

Know any other good tools? LMK.

Lazy Loading

Unless images are part of the layout, you should always be using lazy loading.

Lazy loading will make the page load faster, as images that are offscreen will not be loaded until they are scrolled into view.

All you have to do is add loading="lazy" as an attribute to your img tags, e.g.:

<img src="path-to-img.jpg" alt="Image description" loading="lazy">

You can read more on CSS-Tricks about Native Lazy Loading and The Complete Guide to Lazy Loading Images.

Going the extra step

Your images have been smallified and are lazy, but you want to do a bit more, huh?
Another thing you can do is make sure images are only loading once a user triggers them.

The JS route

This is a technique I employ here, on my website, and it consists of setting a placeholder as the image source and the actual image under a data-src attribute, creating a listener and switching the sources once the user clicks on the image.

Image example:

<img src="/load.png" data-src="https://0xff.nu/i/Tubby-ae0ddc24569cabab.png" alt="Holy fucking unreadable font, Batman!" loading="lazy">

The JS code:

  <script type="text/javascript" defer>
  const images = document.querySelectorAll("img[data-src]");
  images.forEach(function(image) {
      image.addEventListener('click', e => {
          e.target.src = e.target.dataset.src;
          image.removeEventListener('click', e);
      });
  });

The CSS route

If you don't want to use JavaScript (I wouldn't blame you), you can achieve a similar effect using HTML and CSS. You can see a little demo I wrote on Codepen.

The gist is to place the image offscreen or hide it using a CSS rule and use a checkbox element to switch the styling once it's checked.

For example, the HTML:

<div class="fig">
  <input type="checkbox" id="loadimage" name="loadimage">
  <label for="loadimage">Load Image</label>
  <img src="https://images.unsplash.com/photo-1568431477192-52bb13a55088" loading="lazy" alt="A cute hedgehog">
</div>

And the CSS:

.fig {
  display: inline
}

.fig label {
  color: blue;
  cursor: pointer;
  text-decoration: underline;
}

.fig input {
  display: none
}

.fig img {
  position: absolute;
  left: -9999px;
  display: none;
}

.fig input:checked ~ img {
  position: relative;
  left: 0;
  display: block;
}

This might be a bit less straightforward and more cumbersome solution, but it works.

In conclusion

You don't have to do this, and you might argue how this is kind of fucking annoying in terms of UX, especially if you are using a lot of images, and you'd be right and this is exactly where you need to excercise common sense.

Closing words

Images are only part of the web bloat, but they could be one of the easier things to fix. Everything depends on you and how much effort and thought you're willing to put into this.

The important thing is that we acknowledge the problem and take steps towards fixing it, rather than contributing to it.

Let's make the fucking
web nice again, shall we?


  1. Part of my, I guess, way of minimalism, is that when writing code, if something doesn't solve a problem, answer a need or makes someone's life easier it's most likely not required. This is true for many things, images included. I only reserve images for things I cannot show using text. 

Oldest comments (2)

Collapse
 
roniardynt profile image
Ron • Edited

thanks for the article, Paul. it's give me clearly tips and trick about optimizing images asset.
i found this article when i badmood cause look my lighthouse score is terrible especially in image optimization.

Collapse
 
hxii profile image
Paul (hxii) Glushak

Sure thing, Ron! Glad you found it useful.