diff --git a/documentation/slider-read-write.php b/documentation/slider-read-write.php index 35ed2096..676b49c8 100644 --- a/documentation/slider-read-write.php +++ b/documentation/slider-read-write.php @@ -42,6 +42,8 @@

Passing null as the value to setHandle will leave the handle unchanged.

+

Both the set and setHandle methods have an exactInput argument, which can be used to ignore the stepping configured for the slider.

+

To return to the initial slider values, the .reset() method can be used. This will only reset the slider values.

diff --git a/documentation/slider-read-write/write.js b/documentation/slider-read-write/write.js index 26953186..913b91e0 100644 --- a/documentation/slider-read-write/write.js +++ b/documentation/slider-read-write/write.js @@ -11,13 +11,19 @@ slider.noUiSlider.set([150]); slider.noUiSlider.set([null, 14]); // On a slider with three handles, -// set the third to 12 (the handleNumber is 0-indexed) -// Then: fire the set event -slider.noUiSlider.setHandle(2, 12, true); +// set the third to 12 (the handleNumber is 0-indexed), +// fire the set event (default true), +// Don't ignore stepping on the slider (default false) +slider.noUiSlider.setHandle(2, 12, true, true); // Set both slider handles on a slider with two handles slider.noUiSlider.set([13.2, 15.7]); +// Set both slider handles on a slider with two handles, +// fire the set event (default true) +// Ignore stepping on the slider (default false) +slider.noUiSlider.set([13.2, 15.7], true, true); + // Return to the 'start' values // Does NOT reset any other slider properties slider.noUiSlider.reset(); diff --git a/src/nouislider.js b/src/nouislider.js index d435fcae..0f0ac991 100644 --- a/src/nouislider.js +++ b/src/nouislider.js @@ -2297,8 +2297,11 @@ } // Test suggested values and apply margin, step. - function setHandle(handleNumber, to, lookBackward, lookForward) { - to = checkHandlePosition(scope_Locations, handleNumber, to, lookBackward, lookForward, false); + // if exactInput is true, don't run checkHandlePosition, then the handle can be placed in between steps (#436) + function setHandle(handleNumber, to, lookBackward, lookForward, exactInput) { + if (!exactInput) { + to = checkHandlePosition(scope_Locations, handleNumber, to, lookBackward, lookForward, false); + } if (to === false) { return false; @@ -2363,7 +2366,7 @@ } // Set the slider value. - function valueSet(input, fireSetEvent) { + function valueSet(input, fireSetEvent, exactInput) { var values = asArray(input); var isInit = scope_Locations[0] === undefined; @@ -2378,7 +2381,7 @@ // First pass, without lookAhead but with lookBackward. Values are set from left to right. scope_HandleNumbers.forEach(function(handleNumber) { - setHandle(handleNumber, resolveToValue(values[handleNumber], handleNumber), true, false); + setHandle(handleNumber, resolveToValue(values[handleNumber], handleNumber), true, false, exactInput); }); var i = scope_HandleNumbers.length === 1 ? 0 : 1; @@ -2387,7 +2390,7 @@ // Iterate all handles to ensure constraints are applied for the entire slider (Issue #1009) for (; i < scope_HandleNumbers.length; ++i) { scope_HandleNumbers.forEach(function(handleNumber) { - setHandle(handleNumber, scope_Locations[handleNumber], true, true); + setHandle(handleNumber, scope_Locations[handleNumber], true, true, exactInput); }); } @@ -2409,7 +2412,7 @@ } // Set value for a single handle - function valueSetHandle(handleNumber, value, fireSetEvent) { + function valueSetHandle(handleNumber, value, fireSetEvent, exactInput) { // Ensure numeric input handleNumber = Number(handleNumber); @@ -2418,7 +2421,8 @@ } // Look both backward and forward, since we don't want this handle to "push" other handles (#960); - setHandle(handleNumber, resolveToValue(value, handleNumber), true, true); + // The exactInput argument can be used to ignore slider stepping (#436) + setHandle(handleNumber, resolveToValue(value, handleNumber), true, true, exactInput); fireEvent("update", handleNumber); diff --git a/tests/slider.html b/tests/slider.html index ff36a827..bcb97b3a 100644 --- a/tests/slider.html +++ b/tests/slider.html @@ -73,6 +73,7 @@ + diff --git a/tests/slider_set-exactInput.js b/tests/slider_set-exactInput.js new file mode 100644 index 00000000..f1ab3367 --- /dev/null +++ b/tests/slider_set-exactInput.js @@ -0,0 +1,78 @@ +// #436 +QUnit.test("Set & SetHandle exactInput parameter", function (assert) { + + document.getElementById('qunit-fixture').innerHTML = '
'; + + var slider = document.getElementById('qunit-fixture').querySelector('.slider'); + + var newInput = document.createElement('input'); + newInput.id = 'slider-input'; + document.getElementById('qunit-fixture').insertBefore(newInput, slider); + + noUiSlider.create(slider, { + start: 3000, + range: { + 'min': [0, 1000], + 'max': [10000] + }, + tooltips: true + }); + + newInput.addEventListener('change', (event) => { + var value = parseFloat(event.target.value); + slider.noUiSlider.set(value, true, true); + }); + slider.noUiSlider.on('change', function (value) { + if (newInput.value != value){ + newInput.value = value; + } + }); + + assert.equal(slider.noUiSlider.get(), 3000); + + slider.noUiSlider.set(5000); + assert.equal(slider.noUiSlider.get(), 5000); + + slider.noUiSlider.set(4600); + assert.equal(slider.noUiSlider.get(), 5000); + + slider.noUiSlider.set(1200, true, true); + assert.equal(slider.noUiSlider.get(), 1200); + + slider.noUiSlider.set(6789.99, true, true); + assert.equal(slider.noUiSlider.get(), 6789.99); + + slider.noUiSlider.set(2200, true, null); + assert.equal(slider.noUiSlider.get(), 2000); + + slider.noUiSlider.set(300, true, undefined); + assert.equal(slider.noUiSlider.get(), 0); + + slider.noUiSlider.setHandle(0, 8000); + assert.equal(slider.noUiSlider.get(), 8000); + + slider.noUiSlider.setHandle(0, 3400); + assert.equal(slider.noUiSlider.get(), 3000); + + slider.noUiSlider.setHandle(0, 5400, true, true); + assert.equal(slider.noUiSlider.get(), 5400); + + slider.noUiSlider.setHandle(0, 7777.77, true, true); + assert.equal(slider.noUiSlider.get(), 7777.77); + + slider.noUiSlider.setHandle(0, 3200, true, null); + assert.equal(slider.noUiSlider.get(), 3000); + + slider.noUiSlider.setHandle(0, 1800, true, undefined); + assert.equal(slider.noUiSlider.get(), 2000); + + newInput.value = 8888.99; + slider.noUiSlider.on('change.one', function (value) { + assert.equal(value, 8888.99); + }); + + newInput.value = "321.54"; + slider.noUiSlider.on('change.two', function (value) { + assert.equal(value, 321.54); + }); +});