Responsive images
What and why are responsive images?
Responsive images let you serve different image formats and sizes to optimise loading time. Serving images in the correct size not only optimises loading time, but rendering time as well, since the browser won't have to downsample the image to its displayed size.
How to serve responsive images?
First, you need to define the appropriate image sizes for you website. You shouldn't offer too many sizes, since each individual image variation will occupy storage space on your server.
Without getting too much into the weeds, the optimal image size is not only defined by its display size, but also by the DPR (device pixel ratio) of the device it is displayed on. The DPR is the ratio between the physical size of the image and the size of the device's screen. For example, a 1920x1080 image on a 2x DPR device will be displayed at a size of 3840x2160. Keeping that in mind, here are some common images sizes to consider:
- 640px - Small mobile (320px logical × 2x DPR)
- 960px - Small mobile high-end (320px × 3x DPR)
- 1200px - Medium mobile/tablet (400-600px logical × 2x DPR)
- 1800px - Tablet/small desktop with high DPR
- 2560px - Large desktop (1280px × 2x DPR)
- 3840px - 4K displays and high-DPR large screens
Generating the various images
Since resizing every image to all the different sizes is a tedious task, we can use a tool like ImageMagick to generate all the images for us. To do so, we first need to install HomeBrew, which is a package manager for macOS.
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
Once HomeBrew is installed, install ImageMagick using the
brew install imagemagick command.
Download the bash script using the following link:
batch-resize-and-convert.sh. Move the script inside the folder containing the images. Then,
get the folder's path (opt + right click
the folder in your file explorer, and select "Copy folder-name as
Pathname") and run the following command:
cd /path/to/folder
# Makes the script executable
chmod +x batch-resize-and-convert.sh
# Run the script
./batch-resize-and-convert.sh
You should now have a new folder named
resized containing all the
images in all the different sizes, both in JPEG and WebP format.
Using the images
To use the images, you can use the
srcset
attribute. The
srcset
attribute allows you to specify different image sources for
different screen sizes. The attribute value is a comma-separated
list of image source strings, each followed by a width descriptor
(600w). If you want to offer multiple image format, wrap the
<img>
tag in a
<picture>
tag and place a
<source>
tag before the
<img>
tag for each format.
Here is an example of a responsive image with a
picture tag. For demonstative
purposes, I've altered the default behaviour of the
srcset
to reload the image when the window is resized. This usually only
happens if the previous source is smaller than the new one.
<picture>
<source srcset="assets/media/resized/placeholder-480w.webp 480w,
assets/media/resized/placeholder-800w.webp 800w,
assets/media/resized/placeholder-1200w.webp 1200w,
assets/media/resized/placeholder-1920w.webp 1920w,
assets/media/resized/placeholder-2560w.webp 2560w"
type="image/webp">
<source srcset="assets/media/resized/placeholder-480w.jpg 480w,
assets/media/resized/placeholder-800w.jpg 800w,
assets/media/resized/placeholder-1200w.jpg 1200w,
assets/media/resized/placeholder-1920w.jpg 1920w,
assets/media/resized/placeholder-2560w.jpg 2560w"
type="image/jpeg">
<img src="assets/media/placeholder.jpg" alt="Grey placeholder rectangle" />
</picture>
Displayed image: placeholder.jpg