This post is part of the Series taxonomy in Hugo series.

As I have written before; I like the concept of blog post series. Break a large topic, or ongoing project, into multiple posts — while maintaining the chronological order.

But one key factor for a successful series implementation is the ease at which the read can navigate through the posts. And orient themselves within the series — meaning; understand where in the series they are currently reading.

My latest improvement on my series implementation is navigation buttons, for the previous and next post 👍

The configuration

I’ve already covered how to create and use taxonomies in the previous post, but here is a super short recap.

Add series to the Hugo configuration:

[taxonomies]
  tag = "tags"
  series = "series"

And define it in the post front matter:

series = ["Home network v2", "Network cabling"]

The old

Let’s first have a look at the old implementation — this series overview was shown at the bottom of posts in a series:

Screenshot of my old series post footer

It works, but has two problems:

  • If the series has lots of posts; the list becomes very long
  • It’s not immediately clear where you are, and how to get to the next post

This can be improved.

The new

With the new implementation; the complete list of posts is normally collapsed. I think this makes sense — because, what the reader typically want, is to get to the next post.

It feels less overwhelming — the information is there, should you need it, but normally hidden:

Screeenshot of my new series post footer

The navigation buttons are of course only visible if there is a previous, or next, post.

*click* Nice! 🍻

The how

When investigating how to navigate a taxonomy in Hugo — I didn’t find many good implementations. In fact; I think my implementation is the cleanest I’ve seen so far.

As before; at the bottom of the single.html layout, there is a partial — series.html:

{{- if .Params.series -}}
  <div class="post-series-bottom">
    {{ partial "series.html" . }}
  </div>
{{- end -}}

And here is that partial. I won’t go into too much detail here — if you know a little Hugo templating, this should be fairly easy to understand:

{{- with (.GetTerms "series") -}}
  {{- range . -}}
    <div class="pagination__title">
      <span class="pagination__title-h">
          {{ .Title }} series
      </span>
      <hr />
    </div>
    {{- $series := .Pages.ByDate -}}
    <details class="entry-toc">
      <summary>
        <span class="entry-toc-header">
          All posts in <strong>{{ .Title }}</strong> series
        </span>
      </summary>
      <ol>
        {{- range $series -}}
        <li>
          {{- if eq .File.UniqueID $.File.UniqueID -}}
            <b>{{ .Title }}</b>
          {{- else -}}
            <a href="{{ .Permalink }}">{{ .Title }}</a>
          {{- end -}}
        </li>
        {{- end -}}
      </ol>
    </details>

    {{- $curPageIndex := 0 -}}
    {{- range $idx, $page := .Pages.ByDate -}}
      {{- if eq $page $ -}}
        {{ $curPageIndex = $idx }}
      {{- end -}}
    {{- end -}}

    {{- $prevPageIndex := sub $curPageIndex 1 -}}
    {{- $nextPageIndex := add $curPageIndex 1 -}}

    <div class="pagination__buttons" style="margin-top: 50px">
    {{- with (index .Pages.ByDate $prevPageIndex) -}}
      <span class="button previous">
        <a href="{{ .Permalink }}" title="{{ .Title }}">
          <span class="button__icon"></span>
          <span class="button__text">{{ .Title }}</span>
        </a>
      </span>
    {{- end -}}
    {{- with (index .Pages.ByDate $nextPageIndex) -}}
      <span class="button next">
        <a href="{{ .Permalink }}" title="{{ .Title }}">
          <span class="button__text">{{ .Title }}</span>
          <span class="button__icon"></span>
        </a>
      </span>
    {{- end -}}
    </div>

  {{- end -}}
{{- end -}}

The key section is this:

{{- $curPageIndex := 0 -}}
{{- range $idx, $page := .Pages.ByDate -}}
  {{- if eq $page $ -}}
    {{ $curPageIndex = $idx }}
  {{- end -}}
{{- end -}}

{{- $prevPageIndex := sub $curPageIndex 1 -}}
{{- $nextPageIndex := add $curPageIndex 1 -}}

Here; the previous, current, and next page index is defined.

I won’t be covering the styling, that feel outside of the scope for this post, and must be adapter to theme you are using anyway.

Try it

As this post is part of a series, you can try the new implementation below 👇

A post about series, in a series, that’s meta!

🖖

Series taxonomy in Hugo series
All posts in Series taxonomy in Hugo series
  1. Creating a series taxonomy in Hugo
  2. Adding support for multiple series per post — in Hugo
  3. Implementing series navigation buttons — in Hugo