Hide HTML elements based on HTMX request status

By

Learn how to show or hide HTML elements based on the HTMX request status, targeting the htmx-request and htmx-added classes with custom Tailwind variants.

~~~

To show or hide elements based on the status of an HTMX request, target the CSS classes HTMX adds during the request lifecycle. You can do it with plain CSS, or with custom Tailwind variants.

HTMX lets us create an HTTP request pretty easily using hx-get or hx-post, etc.

The request lifecycle goes through a set of stages: request, swapping, settling, added (see https://htmx.org/docs/#request-operations)

At each stage, HTMX adds a class to the elements involved:

HTMX request order of operations showing lifecycle stages and CSS classes like htmx-request, htmx-swapping, htmx-added, and htmx-settling

You can target those classes with CSS to add transitions or whatever to the elements based on the state of the request.

For example, this dims a button while its request is running:

button.htmx-request {
  opacity: 0.5;
}

There’s also htmx-indicator, but that one works the other way around: it’s a class you put on a spinner element, and HTMX makes it visible only during requests.

Styling the lifecycle classes with Tailwind

Using Tailwind CSS, you can use a “trick” to style those with variants.

You can configure variants in your tailwind.config.js file:

//...
  plugins: [
    plugin(function({ addVariant }) {
      addVariant('htmx-settling', ['&.htmx-settling', '.htmx-settling &'])
      addVariant('htmx-request', ['&.htmx-request', '.htmx-request &'])
      addVariant('htmx-swapping', ['&.htmx-swapping', '.htmx-swapping &'])
      addVariant('htmx-added', ['&.htmx-added', '.htmx-added &'])
    }),
  ],
//...

Each variant maps to two selectors. &.htmx-request matches when the element itself has the class. .htmx-request & matches when any ancestor has it. That second one is handy: you can style children of the element making the request.

Now you can use those variants like this:

<button class="htmx-added:opacity-0 opacity-100 transition-opacity duration-1000">
  click this
</button>

When HTMX inserts this button into the page, it carries the htmx-added class, so it starts fully transparent. Once it settles, HTMX removes the class, and the transition fades it in over one second.

A pitfall with the config

The plugin function doesn’t exist by default in the config file. You need to require it at the top:

const plugin = require('tailwindcss/plugin')

Forget that and the build fails with plugin is not defined. Easy to miss when copy-pasting the variants snippet.

Tagged: htmx · All topics
~~~

Related posts about htmx: