Image Optimization - A Practical Guide for Web Developers to Optimize Images
Tags: webdev, webperf, imageoptimization
Published: 2024-05-04 08:06:06

This guide primarily targets web developers who want to optimize images for media-heavy web and mobile applications. While we will cover some essential theories to solidify your understanding of the core concepts, the main focus of this guide is on practical tips and techniques.

Based on our extensive experience working with thousands of developers, we have compiled a set of opinionated, actionable recommendations and a checklist to enhance your applications' image performance.

Ready to dive in? Let's get started!

## Chapter 1 - What is image optimization?

Image optimization is a set of techniques to reduce image file size without compromising "perceived" image quality. The goal is to make images load faster on web and mobile applications. Techniques that are used for image optimization include:

* **Image compression** - Reducing the file size of an image while maintaining visual quality using lossy compression techniques.
* **Image resizing** - Changing the dimensions of an image on the server side to fit the application layout on the front end.
* **Image format selection** - Choosing the right output image format based on the image content and device.
* **Lazy loading** - Loading images only when the user is about to see them on the screen.
* **Content Delivery Network (CDN)** - Using a CDN to deliver images faster to users around the world.

We will cover each of these techniques in detail in the following chapters. But first, let's see an example and understand why image optimization is important.

### Quick example of image optimization

Let's take this 1.2MB JPEG image as an example and see how we can optimize it using image compression and format selection.

```html
<!-- Using q to control compression on a scale of 1 to 100 -->

<!-- Original image - 1.2MB -->
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=f-jpg,q-100" />

<!-- Webp with compression - 72 KB -->
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=f-webp,q-80" />

<!-- AVIF with compression - 43 KB -->
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=f-avif,q-80" />
```

We have put a screenshot instead of rendering actual images because your browser might not support AVIF or WebP format.

![](https://ikmedia.imagekit.io/site-guides/image-optimization-example.png?updatedAt=1713413904257)

## Chapter 2 - Importance of image optimization

It is a no-brainer that images are the most engaging content on the web after video. They help convey information, create visual interest, and improve user engagement. But what if those images are not loaded quickly enough?

Slow-loading images on a website leads to -

* **Poor user experience** - Users are less likely to engage with a website that takes too long to load images.
* **Higher bounce rates** - Users are more likely to leave a website if images take too long to load.
* **Lower conversion rates** - Slow-loading images will negatively impact conversion rates on e-commerce websites.

### But what is quick enough?

The answer to this question has been very subjective until recently. The performance is relative, what is fast for one user might be slow for another. For example:

* What is fast on a high-speed internet connection might be slow on a poor connection.
* What is fast on a high-end desktop might be slow on a low-end mobile device.
* What is fast for a user in the US might be slow for a user in India.

Often, the methods used by engineering teams to measure "speed" are not always accurate. Most of the time, what we measure in a controlled and simulated environment doesn't match the real-world performance.

This led to the creation of standard user-centric performance metrics that website developers can use to answer the questions confidently - "Is my website fast enough?" and "Are my images loading quickly enough?".

This is what core web vitals are all about. They are a set of metrics that Google has introduced to measure the user experience on a website. They are based on real-world data and are designed to help developers understand how fast their website is loading for users.

## Chapter 3 - Core web vitals for image performance

Core Web Vitals are the most crucial user-centric performance metrics that site owners should continuously measure and improve. Google has simplified the measurement of these metrics by providing the [Google PageSpeed Insights](https://pagespeed.web.dev/) tool.

A typical report of Google PageSpeed Insights looks like this:

![Screenshot of core web vitals](https://ikmedia.imagekit.io/site-guides/screenshot-of-core-web-vitals.png?updatedAt=1713336644748)

> Many metrics are part of [Core Web Vitals](https://web.dev/articles/vitals), but image optimization has a direct impact on Largest Contentful Paint (LCP) and First Contentful Paint (FCP).

### Largest Contentful Paint (LCP)

It represents how quickly the main content of a web page loads, specifically, the time from when the user initiates loading the page until the largest image or text block is rendered within the viewport. To provide a good user experience, LCP should occur within 2.5 seconds of when the page first starts loading. Fast-loading images will have a direct positive impact on this metric.

![Source web.dev](https://ikmedia.imagekit.io/site-guides/lcp.png?updatedAt=1713337648051)

### First Contentful Paint (FCP)

It marks the time at which the first content is painted. It is the first impression of the website. For this metric, "content" refers to text, images (including background images), elements, or non-white elements. If you have an image like a banner at the top of the page, its loading time will directly impact the FCP. To provide a good user experience, pages should have a FCP of less than 1.8 seconds.

![Source web.dev](https://ikmedia.imagekit.io/site-guides/fcp.png?updatedAt=1713337648051)

## Chapter 4 - Image optimization Checklist

Here is a checklist for your team to ensure that images on your website are optimized for performance. This checklist is based on the best practices and techniques we will cover in the following chapters.

<table border="1">
  <tr>
    <th style="width: 30%">Task</th>
    <th>Description</th>
  </tr>
  <tr>
    <td>Compress images<br><code>HIGH IMPORTANCE</code></td>
    <td>Choosing the correct compression settings allows for a balance between image quality and file size, which speeds up image loading without compromising visual clarity.</td>
  </tr>
  <tr>
    <td>Adopt WebP/AVIF<br><code>HIGH IMPORTANCE</code></td>
    <td>Modern image formats like WebP or AVIF can significantly reduce file size while maintaining high-quality visuals, leading to faster loading times.</td>
  </tr>
  <tr>
    <td>Correctly resize images on server-side<br><code>HIGH IMPORTANCE</code></td>
    <td>Serving images at the correct dimensions reduces unnecessary data overhead, enhancing speed and efficiency in image delivery</td>
  </tr>
  <tr>
    <td>Utilize a CDN<br><code>HIGH IMPORTANCE</code></td>
    <td>A Content Delivery Network (CDN) enhances image delivery by serving them from a server closest to the user. This proximity significantly reduces load times and improves response rates, optimizing the user experience across different global locations.</td>
  </tr>
  <tr>
    <td>Implement responsive images<br><code>MEDIUM IMPORTANCE</code></td>
    <td>Ensure that your application loads the right image. Consider implementing responsive images using srcset and size attributes.</td>
  </tr>
  <tr>
    <td>Replace GIFs with video<br><code>MEDIUM IMPORTANCE</code></td>
    <td>Replacing GIFs with videos or animated WebP reduces file size and load times while saving bandwidth costs.</td>
  </tr>
  <tr>
    <td>Set image dimensions<br><code>MEDIUM IMPORTANCE</code></td>
    <td>Specifying width and height on images prevents layout shifts during loading, improving user experience and Cumulative Layout Shift scores.</td>
  </tr>
  <tr>
    <td>Use SVGs for icons<br><code>MEDIUM IMPORTANCE</code></td>
    <td>Vector images like SVGs are ideal for logos and icons as they scale without losing quality, are smaller in file size, and render sharply on all screen resolutions.</td>
  </tr>
  <tr>
    <td>Implement lazy loading<br><code>MEDIUM IMPORTANCE</code></td>
    <td>Lazy loading defers loading of images until they are in or near the viewport, reducing initial load time and saving bandwidth costs.</td>
  </tr>
  <tr>
    <td>Use preconnect and priority hints<br><code>LOW IMPORTANCE</code></td>
    <td>Preconnect hints enable the browser to establish early connections to domains hosting images, which accelerates image loading when accessed by users. Additionally, using <a href="https://web.dev/articles/fetch-priority" target="_blank">priority hint</a> to prioritize images at the top of the page can enhance the Largest Contentful Paint (LCP), significantly improving the perceived load speed of the page.</td>
  </tr>
  <tr>
    <td>Monitor relevant Core Web Vitals<br><code>HIGH IMPORTANCE</code></td>
    <td>Tracking relevant Core Web Vitals helps identify areas for improvement, ensuring optimal user experience and SEO rankings.</td>
  </tr>
</table>


## Chapter 5 - Compress images

Image compression is the process of reducing the file size of an image without significantly affecting its visual quality. There are two types of image compression techniques:

### Lossy Compression

Lossy compression reduces file sizes by permanently removing certain information and details from image files. While this can affect image quality, the degree of quality loss can be controlled and is often imperceptible, making the trade-off in size reduction very advantageous for web usage.

Predominantly used in web applications, lossy compression is ideal for balancing image quality with load speed, thereby enhancing user experience and reducing data costs. Formats such as JPEG and WebP are commonly used for lossy compression. These are suitable for photographs and detailed images where a slight loss of quality is acceptable in exchange for significantly smaller file sizes.

#### Why does lossy compression work really well for web use cases?

Let's compress a 1.2MB JPEG image at different compression levels and see the difference:

![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yyd6a1xg6us8i8b3coir.png)


You won't notice any difference between the original image (leftmost) and the compressed images, although the file sizes vary significantly. This demonstrates the effectiveness of lossy compression for web use, as it reduces file size dramatically without a noticeable change in "perceived" quality to the human eye.

> You should avoid extreme image compression, as there is an optimal balance between file size and quality. Excessive compression results in poor visual quality, negatively impacting user experience. An image CDN like ImageKit.io is valuable for its real-time optimization capabilities. It automatically compresses images to the appropriate level, which balances visual quality & size and allows you to control this compression based on your business requirements.

### Lossless Compression

Lossless compression reduces file size without any loss of information. It optimizes the image data by repackaging redundant data and removing unnecessary metadata, ensuring that the original data can be perfectly reconstructed from the compressed data. Lossless compression is crucial for archiving images where preserving the original quality is essential. It is also recommended for images that undergo multiple edits, as it prevents the quality degradation that can occur with repeated saving.

PNG and TIFF are typical formats that employ lossless compression. They are preferred for images requiring high precision and clarity, such as digital graphics, logos, and line art.

> We don't recommend using lossless compression for web use cases.

### How to compress images?

There are many online and offline tools available to compress images. We highly recommend using only the online tools or an Image CDN as they don't require installation.

Depending on the use case, you can choose the right tool for compressing images:

<table style="text-align:left;">
    <thead>
        <tr>
            <th>Use-case</th>
            <th style="text-align:left;">Tool</th>
        </tr>
    </thead>
    <tbody>
        <tr>
            <td>Very few images. One-time optimization is required.</td>
            <td style="text-align:left;"><a href="https://tinypng.com/">TinyPNG</a> and <a
                    href="https://squoosh.app/">Squoosh</a>.</td>
        </tr>
        <tr>
            <td>E-commerce website</td>
            <td style="text-align:left;">
                Depending on the platform, there could be some built-in optimizations. However, platforms like Magento,
                WordPress, and Shopify often result in poor visual quality of the images. We recommend using an image CDN like ImageKit.io. For more details on how to display high-quality e-commerce product images, <a href="https://imagekit.io/how-to-show-high-quality-e-commerce-product-images/" target="_blank"> checkout this blog</a>.
                <br />
                <br />
                <ul>
                  <li>
                    Learn how Nykaa simplified image management and optimization for their websites and apps. <a href="https://imagekit.io/blog/nykaa-image-management-optimization-imagekit-case-study/" target="_blank">Case study</a>.
                  </li>
                  <li>
                    Lenskart leveraged better visual experience to improve conversion and global expansion. <a href="https://imagekit.io/blog/how-lenskart-improved-conversion-and-global-expansion-using-better-visual-experience/" target="_blank">Case study</a>.
                  </li>
                </ul>
            </td>
        </tr>
        <tr>
            <td>Custom media-heavy web application</td>
            <td style="text-align:left;">
              Use an image CDN to automate image
                optimization. This allows your engineering team to focus on building an engaging visual experience
                without dealing with its technical complexities.
                <br />
                <br />
                <ul>
                  <li>
                    Checkout how Swiggy enhanced performance, personalized UX, and saved costs across platforms. <a href="https://imagekit.io/blog/swiggy-imagekit-case-study/" target="_blank">Case study</a>.
                  </li>
                  <li>
                    Learn how Curtsy improved customer engagement and transactions with personalized banners. <a href="https://imagekit.io/blog/improving-customer-engagement-and-transactions-with-personalized-banners-curtsy-case-study/" target="_blank">Case study</a>.
                  </li>
                </ul>
            </td>
        </tr>
        <tr>
            <td>User-generated content</td>
            <td style="text-align:left;">
                To manage user-generated content effectively, you have two options for image compression: compress at
                the time of upload and store the compressed images, or use on-the-fly compression via an image CDN. For storage, consider using cloud-based object storage like S3 or opt for ImageKit's Media Library. ImageKit's <a href="https://imagekit.io/blog/image-storage-api/" target="_blank">storage API</a> allows you to compress images and apply various transformations during uploading. You can use the generated media file URLs directly in your application.
            </td>
        </tr>
    </tbody>
</table>

> You should always store high-quality master images at the largest resolution needed for desktop use, typically around 1920px wide and under 5MB. This approach lets you tweak compression settings later without losing the original image quality. Having an image CDN that can compress images on the fly is recommended, as it gives your engineering team the flexibility to adjust compression settings without altering the original image.

## Chapter 6 - Optimizing image format

Optimizing image format means converting the input image to the right output format before delivering it to the user.

### What is the right image format?

Well, it depends on a lot of things. You should consider the following factors - 

* **Browser and device support** - Does the browser support modern image formats like WebP and AVIF?
* **Transparency** - Does the image require transparency? JPEG doesn't support transparency, so possible options are PNG, WebP, and AVIF.
* **Animation** - Does the image require animation? GIF and WebP support animation.
* **Compression/File size** - AVIF is the clear winner in terms of compression and file size. WebP is also good. JPEG is the worst relatively.
* **Quality** - At similar compression levels, which format delivers superior quality? AVIF leads in quality, with WebP also performing well.

So, the definition of the right image format becomes:

> The right image format is the one that provides high quality and the smallest file size based on the image content and device support. This means that AVIF may be suitable for some users, and JPEG may be the better choice for others.

It is easy to get overwhelmed by these factors. But don't worry; follow these guidelines, and you will be good:

* Use SVG for icons, simple graphics, and logos. A vector image is resolution-independent, so it can be scaled to any size without losing quality. All modern browsers support it.
* For photographs and images with complex color gradients, i.e., typical real-world images, AVIF should be preferred. Use WebP as a decent fallback because it is now widely supported. Use JPEG as a last resort for very older browsers and devices.
* For images requiring transparency, use AVIF or WebP. PNG should be your last preference.
* Avoid using GIFs altogether. Convert GIF to MP4 video or animated WebP.
* If you use a content delivery network (CDN), which you should be, then correctly configure caching rules so images are not delivered in unsupported image format from polluted CDN cache. We will talk more about this in the coming chapters.
* Above all, make sure your application logic is simple. Handle complexity on the server-side.

> If you're setting up an in-house image processing service, consider the high infrastructure costs, especially for computationally intensive tasks like encoding images in AVIF format. An image CDN like ImageKit.io can streamline image processing for you and efficiently handle scaling during traffic spikes.


## How to handle browser support and serve image in the best possible format?

We talked about serving different image formats based on the browser support. But how do you do that?

Technically, you can do it in two ways:

1. **Using HTML `picture` element** - The `picture` element allows you to define multiple sources for an image based on different conditions. You can use it to serve different format images based on browser support.

```html
<picture>
 <source srcset="image.avif" type="image/avif">
 <source srcset="image.webp" type="image/webp">
 <img src="image.jpg" alt="An awesome image">
</picture>
```

2. **Using ImageKit.io** - ImageKit.io is an image CDN that can automatically convert images to the right format based on the factors we discussed above. You don't have to change the image URL. This is done by changing the format on the fly and correctly setting the `Content-Type` response header based on format support declared by the browser in the `Accept` request header.

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg" />
```

### What's wrong with using picture element?

* The problem with using the `picture` element to serve different formats is that it increases the HTML markup. If you are doing server-side rendering, all users will have to download this extra markup when every page loads.
* Another problem is generating and storing multiple variants for the same image. What if a new format comes up tomorrow? You will have to update all the images. This needs to be more scalable.

> The second approach is using an [image CDN](https://imagekit.io). It always delivers an image in the right format, considering all the above factors. You don't have to change the image URL. In addition, you can control the output format via URL parameters.

### How to convert GIF to video or animated WebP?

GIF is not an ideal web format due to its large file size and limited color palette, which supports only 256 colors. It also lack modern features like transparency. For better performance and quality, it is recommended that GIFs be converted to video formats or animated WebP.

Let's convert this GIF - https://ik.imagekit.io/demo/gif-test.gif to webm video and animated WebP to compare sizes.

![Original GIF - 2.3MB](https://ikmedia.imagekit.io/site-guides/gif.png?updatedAt=17136850488663)

![WebM Video - 165KB](https://ikmedia.imagekit.io/site-guides/webm-video.png?updatedAt=17136850488932)

![Animated WebP - 1.4MB](https://ikmedia.imagekit.io/site-guides/animated-webp.png?updatedAt=17136850348509)

Stark difference in file sizes, right? 2.3MB Gif vs 165KB WebM video vs 1.4MB Animated WebP.

#### Convert GIF to video using ImageKit

Use ImageKit [GIF to video](https://docs.imagekit.io/features/video-transformation/resize-crop-and-other-common-video-transformations#gif-to-mp4) conversion feature to convert GIF to video. You can then use the HTML5 video tag for playback. ImageKit will automatically take care of video codec and serve [VP9](https://imagekit.io/blog/vp9-codec/) or [AV1](https://imagekit.io/blog/av1-codec/) encoded video if browser supports it.

```html
<video autoplay loop muted playsinline>
 <source src="https://ik.imagekit.io/demo/gif-test.gif/ik-gif-video.mp4">
</video>
```

#### Convert GIF to animated WebP

When images are delivered using ImageKit, a GIF is automatically converted to animated WebP for supported browsers. You don't have to do anything.

```html
<img src="https://ik.imagekit.io/demo/gif-test.gif">
```

## Chapter 7 - Resizing images to fit the layout

Resizing an image means changing its dimensions on the server-side per layout requirements before delivering it to the user. Many of us have inadvertently uploaded full-size images directly onto web pages. This is an easy mistake to make, especially when fast internet speeds make large images appear to load swiftly and display properly. However, in practical scenarios, this can significantly degrade performance as users are forced to download excessive data, impacting their experience negatively.

### Why resize images on server-side?

Simply put, resizing images to fit the layout is important because it reduces the image's resolution, meaning there are fewer pixels to encode, which results in a smaller file size. Serving a 2000x2000 image in a 200x200 container is inefficient, wasting bandwidth and slowing down image loading times for your users.

## How to resize images?

No matter how your media workflow looks, there are only two ways to serve correctly resized images: either you generate and store the correct-size image in advance, or you generate it on the fly.

* Pre-emptive resizing -  In this approach, you generate and store multiple variants of the image based on the current application layout (and future needs). This is a good approach if you have a static layout that won't change. However, it is not scalable, and you will end up storing multiple copies of the same image.
* On-the-fly resizing - With this approach, you only store the original image and resize it on the fly based on the application layout. This method is highly scalable and recommended for most use cases because it adapts to varying UI changes and device targets without the need to pre-generate and store every possible image variation. This saves on storage and ensures images are optimally sized in real time, catering to the high variability in user devices.

### Pre-emptive resizing using ImageMagick

If there are only a handful of images, use any online image resizing tool. For media-heavy use use-cases, you can programmatically resize images at the time of ingestion and store multiple variants.

To resize all images in a folder to specific dimensions using ImageMagick from the command line, you can use the `mogrify` command. `mogrify` is part of the ImageMagick suite of tools, and it is used for batch processing of image files. Here's how you can do it:

```bash
cd /path/to/your/images
mogrify -resize 200x200 *.jpg
```

> The mogrify command modifies images in place, meaning it will overwrite the original files. It's a good practice to back up your images before running the command, especially if you are not sure about the changes.

### How to resize images on the fly?

On-the-fly resizing is the most scalable approach. You don't have to worry about storing multiple variants of the same image. You can resize images on the fly using an image CDN like ImageKit.io or by implementing an image resizing service yourself.


![Image description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/y69yttrpmpbegd4lkzg2.gif)

#### Basic resizing 200x200 thumbnail

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=w-200,h-200" />
```

#### AI-based smart cropping to generate meaningful thumbnails

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=w-200,h-200,fo-auto" />
```

> See the different [image transformations](https://docs.imagekit.io/features/image-transformations) available in ImageKit.

## How to load the correct image in your application?

We've discussed resizing images to make them suitable for your application. But how do you ensure the correct image loads on each device?

* If your application's layout is simple and consistent across different screen sizes, you can load the image using the `src` attribute. This technique also works on single-page applications (SPAs) where JavaScript generates the layout.
* If the layout is complex and adjusts based on screen size and display density, you should use the `srcset` attribute. This lets you specify multiple image options, ensuring the most suitable one is loaded based on the device's screen size. This technique is part of implementing [responsive images](https://imagekit.io/responsive-images/).

### Implementing responsive images

Responsive images are the set of techniques used to load the right image based on device resolution, orientation, screen size, network connection, and page layout. The browser should load an image that fits the layout, and loading it shouldn't result in time & bandwidth wastage. It improves user experience as images load fast and looks crisp to the human eye.

We have written an end-to-end guide on [responsive images](https://imagekit.io/responsive-images), but here is what you need to know - 

* Use `srcset` with `sizes` to let the browser load the right image based on the device's screen size and application layout. This forces you to consider layout and image dimensions.
* Avoid using the `picture` element and Client Hints to automate responsive image implementation. This method looks promising on the surface, but it will end up creating too many close variants of the same image.
* In most cases, [the human eye cannot discern the benefits of a Device Pixel Ratio (DPR) of 3](https://observablehq.com/@eeeps/visual-acuity-and-device-pixel-ratio), allowing for the use of smaller images without noticeably reducing quality for the majority of users. Limit serving only 2x images for high-density screens like Retina displays.
* Regardless of the chosen method, select breakpoints thoughtfully and maintain straightforward logic. Focus on your users' most common screen sizes and tailor your images to those dimensions. Creating too many variants of the same image can hinder CDN caching and unnecessarily burden the server.

### What is wrong with resizing in HTML using width and height attribute?

Resizing images in HTML using the `width` and `height` attributes is not recommended. It is a bad practice because the browser downloads the full-size image and then resizes it to fit the layout. This wastes bandwidth and slows down page load times. Always resize images on the server-side before delivering them to the user. Furthermore, a browser-resized image might not look as good and sharp as a server-resized image.

## Chapter 8 - Lazy loading images

Lazy Loading Images is a set of techniques in web and application development that defer the loading of images on a page to a later point in time - when those images are actually needed, instead of loading them upfront. These techniques help improve performance, better utilize the device's resources, and reduce associated delivery costs.

We have written a detailed guide on [lazy loading images](https://imagekit.io/blog/lazy-loading-images-complete-guide/), but here is the gist in the context of image performance.

Primarily, there are two advantages of lazy loading images:

* **Performance improvement** - This one is obvious. If a page loads fewer resources, then the important resources like CSS, JS, and images on the top will load faster, improving the overall user experience.
* **Cost reduction** - Serving images from a CDN, S3, web-server or any other provider costs money. If the user never scrolls to the bottom of the page, then why load those images? Lazy-loading images will save you money.

## How to lazy load images?

There are [multiple ways to lazy load images](https://imagekit.io/blog/lazy-loading-images-complete-guide/#lazy-loading-techniques-for-images), but we will suggest you go with the following two:

### Native Lazy Loading
The `loading` attribute on the `img` tag is a native browser feature that allows you to lazy load images without any JavaScript. It is supported in Chrome, Edge, and Firefox.

![Browser support - caniuse.com](https://ikmedia.imagekit.io/site-guides/lazy-loading-support.png?updatedAt=1713755224489)

Here is how you can use it:

```html
<img src="example.jpg" loading="lazy" alt="..." />
```

* **lazy** - Deferring the loading of assets till it reaches a certain distance from the viewport.
* **eager** - loading the assets as soon as the page loads, irrespective of where they are placed on the page, whether above or below the page fold.
* **auto** - This value triggers default lazy loading. Basically, it's the same as not including the loading attribute.

### Intersection Observer API
[Intersection Observer API](https://developer.mozilla.org/en-US/docs/Web/API/Intersection_Observer_API) is a JavaScript API that allows you to observe changes in the intersection of a target element with an ancestor element or with a top-level document's viewport. It is supported in all modern browsers.

Here is a working CodePen example taken from our [blog post](https://imagekit.io/blog/lazy-loading-images-complete-guide/#using-intersection-observer-api-to-trigger-image-loads):

<iframe height="300" style="width: 100%;" scrolling="no" title="Lazy loading images using IntersectionObserver - example code" src="https://codepen.io/imagekit_io/embed/BPXQZZ?default-tab=html%2Cresult" frameborder="no" loading="lazy" allowtransparency="true" allowfullscreen="true">
 See the Pen <a href="https://codepen.io/imagekit_io/pen/BPXQZZ">
 Lazy loading images using IntersectionObserver - example code</a> by ImageKit.io (<a href="https://codepen.io/imagekit_io">@imagekit_io</a>)
 on <a href="https://codepen.io">CodePen</a>.
</iframe>

<br />

> We recommend using the native lazy loading attribute as it is supported in most modern browsers. If you need more control, then use the Intersection Observer API. Loading extra JavaScript for lazy loading images is no longer recommended.

If you are using ImageKit front-end SDKs (React, Angular, Vue.js), check the following getting-started guides:

* Lazy loading images in [React](https://docs.imagekit.io/getting-started/quickstart-guides/react#lazy-loading-images-in-react)
* Lazy loading images in [Angular](https://docs.imagekit.io/getting-started/quickstart-guides/angular#lazy-loading-images-in-angular)
* Lazy loading images in [Vue.js](https://docs.imagekit.io/getting-started/quickstart-guides/vuejs#lazy-loading-images-in-vue.js)

## Chapter 9 - Using CDN for fast download

A [Content Delivery Network](https://imagekit.io/blog/what-is-content-delivery-network-cdn-guide/) (CDN) is a network of servers distributed across the globe that cache and deliver content to users based on their geographic location. CDNs are used to deliver content, including images, videos, and other static assets, faster to users around the world.

### Why use a CDN for images?

* **Faster delivery** - CDNs cache images on servers closer to the user, reducing latency and improving load times.
* **Scalability** - CDNs can handle large volumes of traffic and scale automatically to meet demand.
* **Reliability** - CDNs provide redundancy and failover protection, ensuring that images are always available.
* **Security** - CDNs offer security features like DDoS protection and SSL encryption to protect your web server from common attacks.

## How to configure CDN for images?

Configuring a CDN for images depends on the CDN provider and your image server configuration. In general, here are the factors to keep in mind:

* If your server changes format on the same URL based on the request `Accept` header, then send the `Vary: Accept` response header to cache a different image copy on the CDN. This is important if you serve WebP, AVIF, and JPEG images on the same resource URL. Most CDN providers support this standard except Akamai and Azure CDN from Microsoft.
* Use the `Cache-Control` header to set the cache duration for images. You can set it to a year for images that don't change frequently.
* Correctly set the `Content-Type` header based on the image format.
* Avoid modifying content based on the `User-Agent` request header. First, it is not 100% reliable, and second, it will hit the cache-hit ratio adversely.
* If possible, use CloudFront functions or something similar to normalize the image URL and cache key before caching. This will help in the cache-hit ratio.

> The exact steps to configure a CDN for images could vary from provider to provider, and it can be tricky to get it right. We recommend using an image CDN like ImageKit.io, which automatically takes care of these things for you. It comes with CloudFront CDN.

## Chapter 10 - Platform-specific image optimization

Most site generators and e-commerce platforms have built-in image optimization features. However, they all lack the control and flexibility you need as a web developer to ensure the best image performance. Let's compare some popular platforms and the ideal way to automate image encoding and optimization.

## Image optimization in Next.js

Next.js is a popular React framework that provides server-side rendering and static site generation. The Next.js `Image` component extends the HTML `<img>` element with features for automatic image optimization:

* Format Optimization: Automatically deliver images in the optimal format for each device, utilizing modern formats such as WebP and AVIF.
* Visual Stability: Automatically prevent layout shifts during image loading.
* Lazy Loading: Images load only when they become visible in the viewport, utilizing native browser lazy loading techniques, complemented by optional blur-up placeholders.
* Server-Side Resizing: Perform on-demand resizing of images using the `width` and `height` attributes.

> You can use Next.js built-in optimizations for a small site. For a media-heavy site, you should use an image CDN like ImageKit.io to automate image optimization. Next.js provides custom loader support, so you can use ImageKit.io as a custom loader to serve optimized images.

Here is an example of using ImageKit as a custom loader in Next.js:

```javascript
import Image from "next/image";

const imageKitLoader = ({ src, width, quality }) => {
  if(src[0] === "/") src = src.slice(1);
  const params = [`w-${width}`];
  if (quality) {
    params.push(`q-${quality}`);
  }
  const paramsString = params.join(",");
  var urlEndpoint = "https://ik.imagekit.io/your_imagekit_id";
  if(urlEndpoint[urlEndpoint.length-1] === "/") urlEndpoint = urlEndpoint.substring(0, urlEndpoint.length - 1);
  return `${urlEndpoint}/${src}?tr=${paramsString}`
}

const MyImage = (props) => {
  return (
    <Image
      loader={imageKitLoader}
      src="default-image.jpg"
      alt="Sample image"
      width={400}
      height={400}
    />
  );
};
```

Other useful resources:

* Next.js image optimization [blog post](https://imagekit.io/blog/nextjs-image-optimization/) and [getting started guide](https://docs.imagekit.io/getting-started/quickstart-guides/nextjs).
* Automate [image optimization in WordPress](https://docs.imagekit.io/platform-guides/wordpress) using ImageKit plugin.
* Load high-quality compressed product images on [Shopify](https://docs.imagekit.io/platform-guides/shopify) and [Magento](https://docs.imagekit.io/platform-guides/magento) using ImageKit.

## Conclusion - Why use an image CDN like ImageKit?

To complete image optimization checklist, your engineering team needs a powerful media API to automate most image optimization and transformation tasks. This is where an image CDN comes into play.

### Automate image format selection and compression

ImageKit's automatic format conversion and optimal compression reduce significant complexity for your web developers. Based on multiple factors, including browser support, ImageKit can deliver WebP, AVIF, and JPEG images on the same image URL.

![Loading different image format in Chrome vs Safari on same image URL](https://ikmedia.imagekit.io/site-guides/format-optimization-example.png?updatedAt=1713758900447)

This means you don't have to worry about how to modify HTML to request the correct image or how to store multiple variants of the same image. ImageKit takes care of it for you.

### On-the-fly resizing for responsive images

Implementing responsive images using `srcset` and `sizes` is a relatively complex task. Your team also has to worry about the generation and storage of all the variants. ImageKit can resize images on the fly based on URL parameters, making it easy to serve correctly sized images.

For example, to resize an image to 200x200 pixels, you can use the following URL:

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=w-200,h-200" />
```

To resize an image to 200x200 pixels and apply smart cropping, you can use the following URL:

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=w-200,h-200,fo-auto" />
```

To add a text overlay on the image, you can use the following URL:

```html
<img src="https://ik.imagekit.io/ikmedia/example_image.jpg?tr=w-200,h-200,l-text,i-hello,l-end" />
```

An example picked from our [text overlay blog](https://imagekit.io/blog/css-image-overlay/).

![](https://ik.imagekit.io/ikmedia/hoodie_white.png?tr=w-394,h-540,l-text,i-15%%20OFF,co-FFFFFF,bg-EF6823,r-4,pa-8_8,lx-10,ly-10,tg-bold,fs-30,l-end)

> This is just the tip of the iceberg. ImageKit provides a wide range of [image transformations](https://docs.imagekit.io/features/image-transformations) that can be applied on the fly. Bonus: The same API works on [videos](https://docs.imagekit.io/features/video-transformation), making it a one-stop solution for all your media needs.

## FAQs

## How to monitor image performance?

We recommend using [Google PageSpeed Insights](https://pagespeed.web.dev/) to monitor image performance. It provides a detailed report on how images are affecting your website's performance. You can also use [Lighthouse](https://developers.google.com/web/tools/lighthouse) for a more in-depth analysis. Optimize large contentful paint (LCP) and first contentful paint (FCP) to improve image performance.

## How to optimize images for SEO?

Use sensible file names and alt text for images. Use descriptive file names that include relevant keywords. Add alt text to images to describe the content of the image. This helps search engines understand the context of the image and improves SEO.

## What is Data-Saver mode in Chrome?

Mobile browsers like Chrome Mobile and Opera Mobile allow users to activate a Data Saver mode. With this mode enabled, the browser sends a `Save-data` header within the request. By identifying this header, a web page can customize and deliver an optimized user experience to cost—and performance-constrained users.

ImageKit supports [Data Saver mode](https://docs.imagekit.io/features/image-optimization/data-saver-mode) to further optimize images for users on slow connections.