If I use an input field of type="number" with step="100". I don't want odd numbers to be invalid. I just want increase or decrease to be with a value of 1000.
<input type="number" min="100" max="999999" step="100" />
If the user enters the value "199" and submits, he/she gets an error because the value isn't dividable by 100. But all I want with the step-value is to control the behavior of the spinner, e.g. if the user click up I want the value 199 to become 200 and if he/she clicks down I want it to become 100. Or ideally I would like the value to be increased or decreased with a value of 100.
How do I do this? I tried using the invalid event (with jQuery 1.7.2) like this:
$( "[type='number']" ).bind( 'invalid', function( e ) { var el = $( this ), val = el.val( ), min = el.attr( 'min' ), max = el.attr( 'max' ); if ( val >= min && val <= max ) { return false; } } );
But this results in the form not being submitted.
PS.: This is in Google Chrome 20.0.1132.57 on Fedora 16.
The step attribute specifies the interval between legal numbers in an <input> element. Example: if step="3" , legal numbers could be -3, 0, 3, 6, etc. Tip: The step attribute can be used together with the max and min attributes to create a range of legal values.
Well, first of all thank you for this very interesting question. I've learned a lot about HTML5 validation by searching a solution to your problem.
My research led me to find that HTML5 form validation API has an interesting set of properties that are read-only, but very useful to do what you want.
My approach to your problem was to first add the novalidate
attribute to the form element, so that I can control when to trigger the validation, then read the validity
object attached to the input, so I can know exactly what validation errors are there, and if the only error is stepMismatch
(this is what triggers invalidity of numbers such as 199), I can bypass all the validation process. Else, I can show normal HTML validation behaviour with the reportValidity() method.
Here is the code I came up with that I hope does what you want :
var form = document.querySelector("form") // Get the form var input = document.querySelector("#myInput") // Get the input to validate form.addEventListener("submit", function(e) { e.preventDefault() // Catch the submit // Do the magic if(onlyStepMatters(input.validity)){ form.submit() }else { form.reportValidity() } }) function onlyStepMatters(validityState) { return !( validityState.badInput || validityState.customError || validityState. patternMismatch || validityState.rangeOverflow || validityState.rangeUnderflow || validityState.tooLong || validityState.tooShort || validityState.typeMismatch || validityState.valueMissing ) /* This is what the object looks like, notice I just skipped the stepMismatch */ /* { badInput, customError, patternMismatch, rangeOverflow, rangeUnderflow, stepMismatch, tooLong, tooShort, typeMismatch, valid, valueMissing, } */ }
<form novalidate> <input type="number" id="myInput" min="0" max="1000" step = "100" placeholder="Enter a number" required/> <button type="submit">Send</button> </form>
I'm pretty sure this code could be refactored and become more concise based on the same logic, but I don't have enough time to think more about it.
Any constructive comment will be appreciated.
Hope this helps.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With