This is a concept I first came across a few years back when Lea Verou wrote an article on it. Multi-range sliders have sadly been removed from the spec since, but something else that has happened in the meanwhile is that CSS got better — and so have I, so I recently decided to make my own 2019 version.
In this two-part article, we’ll go through the how, step-by-step, first building an example with two thumbs, then identify the issues with it. We’ll solve those issues, first for the two-thumb case then, in part two, come up with a better solution for the multi-thumb case.
Note how the thumbs can pass each other and we can have any possible order, with the fills in between the thumbs adapting accordingly. Surprisingly, the entire thing is going to require extremely little JavaScript.
Article Series:
- Multi-Thumb Sliders: Particular Two-Thumb Case (This Post)
- Multi-Thumb Sliders: General Case (Coming Tomorrow!)
Basic structure
We need two range inputs inside a wrapper. They both have the same minimum and maximum value (this is very important because nothing is going to work properly otherwise), which we set as custom properties on the wrapper (--min
and --max
). We also set their values as custom properties (--a
and --b
).
- let min = -50, max = 50
- let a = -30, b = 20;
.wrap(style=`--a: ${a}; --b: ${b}; --min: ${min}; --max: ${max}`)
input#a(type='range' min=min value=a max=max)
input#b(type='range' min=min value=b max=max)
This generates the following markup:
Accessibility considerations
We have two range inputs and they should probably each have a , but we want our multi-thumb slider to have a single label. How do we solve this issue? We can make the wrapper a