Range Slider Pro
A native `<input type="range">` with custom track/thumb styling and a live value bubble that follows the thumb. Honest accessibility — keyboard arrows, screen-reader announcement, real form value.
Range Slider Pro the 24th of 28 designs in the 28 CSS Input Field Designs collection. The design pairs CSS styling with a small amount of JavaScript for interactivity. Copy the HTML, CSS and JavaScript panels below into your project — the JS is self-contained, has zero dependencies, and is safe to drop into any framework (React, Vue, Svelte, plain HTML). The design honours prefers-reduced-motion and uses real semantic markup, so it ships accessibility-ready out of the box.
Live preview
The code
<label class="if-range" for="if-range-input">
<span class="if-range-label">Volume <span class="if-range-bubble" data-if-bubble>50</span></span>
<input
id="if-range-input"
type="range"
name="volume"
min="0"
max="100"
value="50"
data-if-range
/>
</label> .if-range {
display: grid;
gap: 8px;
width: 100%;
max-width: 280px;
}
.if-range-label {
display: flex;
justify-content: space-between;
align-items: center;
font-family: "JetBrains Mono", monospace;
font-size: 10px;
letter-spacing: 0.12em;
color: #b8b6d4;
text-transform: uppercase;
}
.if-range-bubble {
font:
700 11px/1 "JetBrains Mono",
monospace;
color: #f0eeff;
background: #7c6cff;
padding: 3px 7px;
border-radius: 999px;
letter-spacing: 0;
}
.if-range input {
width: 100%;
height: 6px;
-webkit-appearance: none;
appearance: none;
background: linear-gradient(
90deg,
#7c6cff 0%,
#7c6cff var(--if-range-fill, 50%),
rgba(255, 255, 255, 0.08) var(--if-range-fill, 50%),
rgba(255, 255, 255, 0.08) 100%
);
border-radius: 999px;
outline: none;
cursor: pointer;
}
.if-range input::-webkit-slider-thumb {
-webkit-appearance: none;
appearance: none;
width: 18px;
height: 18px;
background: #fff;
border: 0;
border-radius: 50%;
box-shadow: 0 2px 6px rgba(124, 108, 255, 0.5);
cursor: pointer;
transition: transform 0.15s;
}
.if-range input::-webkit-slider-thumb:hover {
transform: scale(1.12);
}
.if-range input::-moz-range-thumb {
width: 18px;
height: 18px;
background: #fff;
border: 0;
border-radius: 50%;
box-shadow: 0 2px 6px rgba(124, 108, 255, 0.5);
cursor: pointer;
} // Range Slider Pro — sync the live value bubble + paint the gradient fill via custom property
document.querySelectorAll("[data-if-range]").forEach(function (input) {
var bubble = input.closest(".if-range").querySelector("[data-if-bubble]");
function update() {
var min = Number(input.min) || 0;
var max = Number(input.max) || 100;
var pct = ((Number(input.value) - min) / (max - min)) * 100;
input.style.setProperty("--if-range-fill", pct + "%");
if (bubble) bubble.textContent = String(input.value);
}
input.addEventListener("input", update);
update();
});