Lightweight JavaScript range slider with no dependencies
—
Quality
Pending
Does it follow best practices?
Impact
Pending
No eval scenarios have been run
Runtime configuration updates and slider reconfiguration capabilities for dynamic slider behavior modification.
Updates slider configuration at runtime, allowing dynamic reconfiguration without recreating the slider.
/**
* Update slider configuration at runtime
* @param optionsToUpdate - Partial configuration object with options to update
* @param fireSetEvent - Whether to fire 'set' event after update (default: undefined -> true)
*/
slider.noUiSlider.updateOptions(
optionsToUpdate: Partial<SliderOptions>,
fireSetEvent?: boolean
): void;Usage Examples:
// Update range dynamically
slider.noUiSlider.updateOptions({
range: {
'min': 0,
'max': 200 // Changed from 100 to 200
}
});
// Update multiple options
slider.noUiSlider.updateOptions({
step: 5,
margin: 10,
animate: false
});
// Update without triggering events
slider.noUiSlider.updateOptions({
start: [30, 70]
}, false);Access to the current configuration object.
/**
* Current slider configuration (read-only)
*/
slider.noUiSlider.options: SliderOptions;Usage Examples:
// Get current configuration
const currentConfig = slider.noUiSlider.options;
console.log('Current range:', currentConfig.range);
console.log('Current step:', currentConfig.step);
// Use current config to make conditional updates
if (currentConfig.step !== 10) {
slider.noUiSlider.updateOptions({ step: 10 });
}Update the value range and stepping configuration.
// Basic range update
slider.noUiSlider.updateOptions({
range: {
'min': -50,
'max': 150
}
});
// Complex range with stepping
slider.noUiSlider.updateOptions({
range: {
'min': [0, 1], // Min 0, step 1
'25%': [25, 5], // At 25%, value 25, step 5
'75%': [75, 10], // At 75%, value 75, step 10
'max': 100
}
});Update the step size for value increments.
slider.noUiSlider.updateOptions({
step: 0.5 // Changed from integer to decimal stepping
});Update initial/current values (will reposition handles).
slider.noUiSlider.updateOptions({
start: [25, 75] // Moves handles to new positions
});Update minimum distance between handles.
slider.noUiSlider.updateOptions({
margin: 15 // Handles must be at least 15 units apart
});Update maximum distance between handles.
slider.noUiSlider.updateOptions({
limit: 50 // Handles cannot be more than 50 units apart
});Update padding from slider edges.
// Symmetric padding
slider.noUiSlider.updateOptions({
padding: 10
});
// Asymmetric padding
slider.noUiSlider.updateOptions({
padding: [5, 15] // 5 from start, 15 from end
});Toggle snap-to-step behavior.
slider.noUiSlider.updateOptions({
snap: true // Enable snapping to step values
});Toggle animation behavior.
slider.noUiSlider.updateOptions({
animate: false // Disable smooth animations
});Update value formatting.
// Switch to percentage formatting
slider.noUiSlider.updateOptions({
format: {
to: function(value) {
return value.toFixed(1) + '%';
},
from: function(value) {
return parseFloat(value.replace('%', ''));
}
}
});Update tooltip configuration.
// Enable tooltips
slider.noUiSlider.updateOptions({
tooltips: true
});
// Custom tooltip formatting
slider.noUiSlider.updateOptions({
tooltips: {
to: function(value) {
return '$' + Math.round(value);
}
}
});
// Per-handle tooltip configuration
slider.noUiSlider.updateOptions({
tooltips: [true, false] // First handle has tooltip, second doesn't
});Update scale markers.
// Add pips
slider.noUiSlider.updateOptions({
pips: {
mode: 'count',
values: 5,
density: 3
}
});
// Remove pips
slider.noUiSlider.updateOptions({
pips: null
});// Adjust range based on data availability
function updateSliderRange(minValue, maxValue) {
slider.noUiSlider.updateOptions({
range: {
'min': minValue,
'max': maxValue
}
});
// Ensure current values are within new range
const currentValues = slider.noUiSlider.get();
const adjustedValues = currentValues.map(val => {
const num = parseFloat(val);
return Math.max(minValue, Math.min(maxValue, num));
});
slider.noUiSlider.set(adjustedValues);
}
// Usage
updateSliderRange(0, 500); // Expand range
updateSliderRange(10, 90); // Contract range// Adjust configuration based on screen size
function updateSliderForScreenSize() {
const isMobile = window.innerWidth < 768;
slider.noUiSlider.updateOptions({
step: isMobile ? 10 : 1, // Larger steps on mobile
margin: isMobile ? 20 : 5, // More margin on mobile
tooltips: isMobile ? false : true // No tooltips on mobile
});
}
// Apply on resize
window.addEventListener('resize', updateSliderForScreenSize);
updateSliderForScreenSize(); // Initial setup// Switch between different slider modes
function switchSliderMode(mode) {
switch (mode) {
case 'currency':
slider.noUiSlider.updateOptions({
format: {
to: value => '$' + Math.round(value).toLocaleString(),
from: value => Number(value.replace(/[$,]/g, ''))
},
step: 100,
tooltips: true
});
break;
case 'percentage':
slider.noUiSlider.updateOptions({
format: {
to: value => value.toFixed(1) + '%',
from: value => parseFloat(value.replace('%', ''))
},
step: 0.1,
tooltips: true
});
break;
case 'simple':
slider.noUiSlider.updateOptions({
format: {
to: value => Math.round(value).toString(),
from: Number
},
step: 1,
tooltips: false
});
break;
}
}// Update options based on current state
function updateSliderBasedOnValue() {
const values = slider.noUiSlider.get();
const maxValue = Math.max(...values.map(parseFloat));
if (maxValue > 80) {
// High values - use larger steps and different formatting
slider.noUiSlider.updateOptions({
step: 10,
format: {
to: value => 'High: ' + Math.round(value),
from: value => Number(value.replace('High: ', ''))
}
});
} else {
// Normal values
slider.noUiSlider.updateOptions({
step: 1,
format: {
to: value => Math.round(value).toString(),
from: Number
}
});
}
}
// Apply on value changes
slider.noUiSlider.on('change', updateSliderBasedOnValue);// Save and restore slider configuration
function saveSliderConfig() {
const config = {
range: slider.noUiSlider.options.range,
step: slider.noUiSlider.options.step,
margin: slider.noUiSlider.options.margin,
values: slider.noUiSlider.get()
};
localStorage.setItem('sliderConfig', JSON.stringify(config));
}
function restoreSliderConfig() {
const saved = localStorage.getItem('sliderConfig');
if (saved) {
const config = JSON.parse(saved);
slider.noUiSlider.updateOptions({
range: config.range,
step: config.step,
margin: config.margin,
start: config.values
});
}
}
// Auto-save on changes
slider.noUiSlider.on('change', saveSliderConfig);Some options cannot be changed after slider creation and require recreating the slider:
connect - Connection configurationdirection - Text direction (ltr/rtl)orientation - Physical orientation (horizontal/vertical)behaviour - Interaction behaviorskeyboardSupport - Keyboard navigationkeyboardPageMultiplier - Keyboard step multiplierskeyboardDefaultStep - Default keyboard stepcssPrefix - CSS class prefixcssClasses - CSS class namesdocumentElement - Document element reference// These options require slider recreation
function recreateSliderWithNewBehavior() {
const currentValues = slider.noUiSlider.get();
const currentRange = slider.noUiSlider.options.range;
// Destroy current slider
slider.noUiSlider.destroy();
// Create new slider with different behavior
noUiSlider.create(slider, {
start: currentValues,
range: currentRange,
behaviour: 'drag-fixed', // This requires recreation
connect: true
});
}// Some updates may fail if they create invalid configurations
try {
slider.noUiSlider.updateOptions({
range: {
'min': 100,
'max': 0 // Invalid: min > max
}
});
} catch (error) {
console.error('Invalid range configuration:', error.message);
}
// Values outside new range are automatically adjusted
slider.noUiSlider.updateOptions({
range: { 'min': 0, 'max': 50 } // Shrink range
});
// Current values above 50 will be adjusted to 50// Batch updates for better performance
slider.noUiSlider.updateOptions({
range: { 'min': 0, 'max': 200 },
step: 5,
margin: 10,
format: newFormatter
});
// Instead of multiple separate updates:
// slider.noUiSlider.updateOptions({ range: { 'min': 0, 'max': 200 }});
// slider.noUiSlider.updateOptions({ step: 5 });
// slider.noUiSlider.updateOptions({ margin: 10 });
// slider.noUiSlider.updateOptions({ format: newFormatter });Install with Tessl CLI
npx tessl i tessl/npm-nouislider