How to resize/downscale images

An article with lots of images embedded like this ![]() currently puts all the images in their full resolution in the article, wasting a lot of bandwidth.

How do I change my theme so that ![]() renders a downscaled version of the image with a link to its full resolution?

One option is to have two sets of images: original and resized. Then you could create a shortcode, say it’s named img.html:

{{- $resizedURL := .Get "resizedURL" -}}
{{- $originalURL := .Get "originalURL" -}}
{{- $alt := .Get "alt" -}}
{{- $class := .Get "class" -}}
{{- $style := .Get "style" -}}

<a href="{{ $originalURL | relURL }}"><img src="{{ $resizedURL | relURL }}" alt="{{ $alt }}" class="{{ $class }}" style="{{ $style | safeCSS }}"></a>

Then use it like:

{{< img resizedURL="img/some-img.png" originalURL ="img/some-img.png" alt="Some description" class="some-class" style="some-style" >}}

alt, class, and style arguments would be optional


Another option is to use Hugo Image Processing. I’m not familiar with this myself, so someone else would have to help you there.

2 Likes

I’m trying to avoid the shortcode. Is there a way to hook into the rendering of the ![]() tag?

Also in your example it looks like I need to supply the resized image myself. I would like Hugo to create the downscaled version autoatically.

Not that I know of

Checkout the Image Processing docs I linked previously

2 Likes

The only thing that I can think of that will do what you want is one that I do not recommend doing.

Basically, do a massive find and replace on the content of the page, doing something like the following:

  • Use regex to find every image in .Content
  • Parse the image tag to find the source of the image
  • If the image exists in the assets/ folder or the page bundle, continue
  • Create a Hugo asset out of the image, for processing
  • Use Hugo’s built-in image processing to shrink the image
  • Replace the original image tag with a new one using the smaller image, wrapped in a link to the original file

It’s a really hackish way to do it and is more likely to cause issues. The more sustainable option is to make a shortcode like @zwbetz suggested. But what you want to do is technically possible.

1 Like

Thank you @zwbetz and @Shadow53. This is my current solution:

File /layouts/shortcodes/img.html:

{{ $original := .Page.Resources.GetMatch (.Get 0) }}
{{ $preview := $original.Resize "636x" }}
{{ $alt := .Get 1 }}

{{ if lt $original.Width 636 }}
<img src="{{ $original.RelPermalink }}" width="{{ $original.Width }}" alt="{{ $alt }}">
{{ else }}
<a href="{{ $original.RelPermalink }}" target="_blank" title="{{ $alt }}">
	<img src="{{ $preview.RelPermalink }}" width="{{ $preview.Width }}" alt="{{ $alt }}">
</a>
{{ end }}

And in my article:

{{< img myimagefile "Alternative text" >}}

This works really well, the images can even be included withithout paths and it works on the front page. Awesome.

However, I’m still interested if I can get Hugo to read Markdown style images ![](). I tried replaceRE within the theme, but the content is already in HTML. Is there a way to run replaceRE before the markdown is rendered to HTML?

1 Like