Create responsive images with gulp-sharp-responsive
Tags: javascript, node, tutorial, productivity
Published: 2021-04-18 14:30:50

---
title: Create responsive images with gulp-sharp-responsive
published: true
description: Use this Gulp plugin to produce optimized images for your web users.
tags: javascript, node, tutorial, productivity
cover_image: https://dev-to-uploads.s3.amazonaws.com/uploads/articles/7690v7y4fyjv9467oy8e.jpg
---

Hello everyone, and welcome to this tutorial. Today I would like to introduce a new plugin for Gulp that I created to optimize images for our web browser users.

## Introducting gulp-sharp-responsive

[gulp-sharp-responsive](https://www.npmjs.com/package/gulp-sharp-responsive) is based on the [Sharp NPM package](https://www.npmjs.com/package/sharp), a fast image processing library, and aims to simplify this tedious task. Making images responsive and declined for differents format becomes simple because we only have to configure it and the rest is done automatically for us.

## Context

For this tutorial, let's imagine we have the following folder:

```txt
.
├── src/
│   └── img/
│       └── lion.jpg
├── .gitignore
├── gulpfile.js
└── package.json
```

Let's say We want to output our lion.jpg image into the folder `dist/img`. We also would like to have images in differents sizes:

- 640 (mobile)
- 768 (tablet)
- 1024 (desktop)

And differents formats:

- jpeg
- webp
- avif

## Using gulp-sharp-responsive

To this purpose, here is how you can use this library. 

### Installation

First, let's install Gulp and this plugin:

```bash
npm install --save-dev gulp gulp-sharp-responsive
```

### Usage

Next, head on your `gulpfile.js` file and append this code:

```javascript
// gulpfile.js
const { src, dest } = require("gulp");
const sharpResponsive = require("gulp-sharp-responsive");
```

Then, let's write our "img" task:

```javascript
// gulpfile.js
const { src, dest } = require("gulp");
const sharpResponsive = require("gulp-sharp-responsive");

const img = () => src("src/img/*.jpg")
  .pipe(sharpResponsive({
    formats: [
      // jpeg
      { width: 640, format: "jpeg", rename: { suffix: "-sm" } },
      { width: 768, format: "jpeg", rename: { suffix: "-md" } },
      { width: 1024, format: "jpeg", rename: { suffix: "-lg" } },
      // webp
      { width: 640, format: "webp", rename: { suffix: "-sm" } },
      { width: 768, format: "webp", rename: { suffix: "-md" } },
      { width: 1024, format: "webp", rename: { suffix: "-lg" } },
      // avif
      { width: 640, format: "avif", rename: { suffix: "-sm" } },
      { width: 768, format: "avif", rename: { suffix: "-md" } },
      { width: 1024, format: "avif", rename: { suffix: "-lg" } },
    ]
  }))
  .pipe(dest("dist/img"));
```

Finally, let's expose this task so that we can use it through `npm run img`

```javascript
// gulpfile.js
const { src, dest } = require("gulp");
const sharpResponsive = require("gulp-sharp-responsive");

const img = () => src("src/img/*.jpg")
  .pipe(sharpResponsive({
    formats: [
      // jpeg
      { width: 640, format: "jpeg", rename: { suffix: "-sm" } },
      { width: 768, format: "jpeg", rename: { suffix: "-md" } },
      { width: 1024, format: "jpeg", rename: { suffix: "-lg" } },
      // webp
      { width: 640, format: "webp", rename: { suffix: "-sm" } },
      { width: 768, format: "webp", rename: { suffix: "-md" } },
      { width: 1024, format: "webp", rename: { suffix: "-lg" } },
      // avif
      { width: 640, format: "avif", rename: { suffix: "-sm" } },
      { width: 768, format: "avif", rename: { suffix: "-md" } },
      { width: 1024, format: "avif", rename: { suffix: "-lg" } },
    ]
  }))
  .pipe(dest("dist/img"));

module.exports = {
  img,
};
```

```json
// package.json
{
  "scripts": {
    "img": "gulp img"
  }
}
```

Now, let's run this task once. In your terminal, run this command:

```bash
npm run img
```

You should see something printed in the console like this:

```bash
$ npm run img

> img     
> gulp img

[14:11:00] Using gulpfile /home/khalyomede/gulpfile.js
[14:11:01] Starting 'build'...
[14:11:01] Starting 'img'...
[14:11:02] Finished 'img' after 1.92 s
[14:11:02] Finished 'build' after 1.93 s
```

And if we inspect our folder tree this is what we should get now:

```txt
.
├── dist/
│   └── img/
│       ├── lions-lg.avif
│       ├── lions-lg.jpg
│       ├── lions-lg.webp
│       ├── lions-md.avif
│       ├── lions-md.jpg
│       ├── lions-md.webp
│       ├── lions-sm.avif
│       ├── lions-sm.jpg
│       └── lions-sm.webp
├── src/
│   └── img/
│       └── lion.jpg
├── .gitignore
├── gulpfile.js
└── package.json
```

## Conclusion

Image responsiveness can be of a good use when you want to improve your web page speed using this HTML technique:

```html
<picture>
  <!-- avif -->
  <source srcset="/img/lion-sm.avif" media="(max-width: 640px)" type="image/avif" />
  <source srcset="/img/lion-md.avif" media="(max-width: 768px)" type="image/avif" />
  <source srcset="/img/lion-lg.avif" media="(max-width: 1024px)" type="image/avif" />
  <!-- webp -->
  <source srcset="/img/lion-sm.webp" media="(max-width: 640px)" type="image/webp" />
  <source srcset="/img/lion-md.webp" media="(max-width: 768px)" type="image/webp" />
  <source srcset="/img/lion-lg.webp" media="(max-width: 1024px)" type="image/webp" />
  <!-- jpeg -->
  <source srcset="/img/lion-sm.jpeg" media="(max-width: 640px)" type="image/jpeg" />
  <source srcset="/img/lion-md.jpeg" media="(max-width: 768px)" type="image/jpeg" />
  <source srcset="/img/lion-lg.jpeg" media="(max-width: 1024px)" type="image/jpeg" />
  <!-- original -->
  <img src="/img/lion.jpeg" class="img-responsive" alt="A lion in the jungle." />
</picture>
```

This way, you are asking the browser:

- To load the most modern image first
- Load an image that fits the viewport width
- Fallback to the `<img>` if a browser doesn't support it

If you check the sizes of each files, we can see users will benefit from newest files format small sizes:

| Image         |     Size |   Weight |
|---------------|---------:|---------:|
| lion.jpg      | Original | 1 330 Ko |
| lions-lg.avif |   1024px |    52 Ko |
| lions-lg.jpg  |   1024px |   141 Ko |
| lions-lg.webp |   1024px |   118 Ko |
| lions-md.avif |    768px |    30 Ko |
| lions-md.jpg  |    768px |    81 Ko |
| lions-md.webp |    768px |    67 Ko |
| lions-sm.avif |    640px |    23 Ko |
| lions-sm.jpeg |    640px |    60 Ko |
| lions-sm.webp |    640px |    51 Ko |

Learn more in this detail post:

{% link https://dev.to/khalyomede/speed-up-your-web-page-loading-with-webp-24bk %}

Thanks for reading this tutorial, I hope you enjoyed it as much as I enjoyed writting for Dev.to!

You can learn more about this library, like how to keep the original file in the output images and much more!

{% github khalyomede/gulp-sharp-responsive %}

Happy optimizations!