Don’t Squash Me: Using min-width on Fluid Images

It‘s pretty common to set max-width: 100% on images in fluid layouts, so that they adapt to fit their container:

img {
    max-width: 100%;
    height: auto;
}

When given room to breath, it'll take up as much space as it needs:

[Procrastination Activity pie chart: a breakdown of time spent on various daily distractions]
An example image in a wide container

And when restricted to a smaller container (e.g. a narrow screen), it'll automatically scale down to fit:

[Procrastination Activity pie chart: a breakdown of time spent on various daily distractions]
Automatically scaling images – cool!

That’s all great.

But there’s a limit to how small some images should reasonably be. The text in this image is barely readable when scaled down for smartphone screens. The user could zoom in of course, but it's annoying to have to zoom in and out while skimming through an article.

Often we’ll be able to apply some design to remedy this: present small screens with a different image which arranges the content more appropriately, for example. But sometimes that isn’t possible… when blindly rendering content from a CMS, for instance.

So, consider using min-width to define the smallest size that it makes sense to render this image:

<img src="path/to/image" style="min-width:25em">

then make its container scroll on overflow:

/* The container is often a grid cell */
.grid__item {
    overflow-x: auto;
}

I originally suggested using overflow-x: scroll, but as rightly pointed out by Tal Ben-Ari in the comments, that will leave a permanent scroll bar on some systems.

That way, when the container is too small, the image will stay at a reasonable size and the user can simply scroll across to see the rest of the image.

Oh no! Inline styles! They’re bad aren’t they?

In this case I don’t think so. That declaration is directly related to the image’s content: it’s defined by the size of the text in the image. So I think it makes absolute sense to declare the minimum width in HTML.

If browser support for the CSS attr() expression were better, I’d be tempted to do it like this:

<img src="path/to/image" data-min-width="25em">
img {
    min-width: attr(data-min-width);
}

… but unfortunately no browsers will recognise that yet (they’ll only recognise attr() when used with the content CSS property for generated content).

Ok, but ems?

Yes – the minimum size of this image is the point at which its text becomes hard to read, for a user used to default font sizes. If a user increases their browser’s font size, the minimum size of this image (and hence the minimum size of the text in the image) will increase too. Nice.

The appropriate minimum size for another image might be the point at which key features are no longer rendered properly on screen, so might be better suited to a minimum width defined in pixels.

Here’s a little demo:

[Procrastination Activity pie chart: a breakdown of time spent on various daily distractions]
When the container is smaller than its min-width, the user can scroll across to see the rest of the image

Of course there are times when this will and won’t be appropriate. There’s certainly an impact on the look of the page. As I mentioned above, it’s great if you can solve this with design.

But when you can’t, I think this little trick can be a quick win to keep things more usuable, or act as a safety net for those corner cases your design didn't consider.