views:

79

answers:

5

Is there any existing jQuery functionality that can test if characters entered into a textbox are either numeric, or valid in a number?

Such as

.00 or 0.00, but not 0.00.00 or 0a

What I'd like to do is catch any invalid characters before they appear in the textbox.

If it's not possible with jQuery, what's the best way to approach this?

I know with JavaScript I can test isNaN() and then return false, but that's going to start getting hairy when I have to account for all possible keystrokes.

+8  A: 

just use a regex match

$('#formelement').val().match(/[-+]?[0-9]*\.?[0-9]+/)

(excluding selector, everything else is plain javascript)

As noted in comments, since you need to do it for each character inserted you have to consider an empty decimal part valid (eg. /[-+]?[0-9]*\.?[0-9]*/)

Since people in comments forces me to be precise I can suggest you how to work out how to use this matching for your purpose (but so you don't let anything to the OP imagination :( )

You can split the regex in 3 regexs, one for the first part (eventual sign and whole part), one for the first part plus the dot symbol and one for the whole number.

You validation routine should accept the input while it's being written if it matches at least one of the threes regex just described and the validation done at the end should accept just when the last regex is matched (since you are submitting the value and you need it to be correct)

Jack
the val() method isn't plain JavaScript either. ;)
Matt Huggins
yeah, it was part of the selector thingy :D
Jack
Shouldn't the second [0-9] also have a '?'
Nico Burns
why? you would limit it to just one decimal digit after the dot..
Jack
+? instead of + because + means one or more? otherwise you cant have a number such as 00. with nothing after that dot? (and its impossible to type a number like 00.00 if you can have 00. first) I might be wrong, I'm fairly new to regex's..
Nico Burns
It depends if you want to allow empty decimal part or not. In any case `+?` will keep `+` behaviour making it not-greedy (match minimum quantity). Maybe you mean't using `*` instead that `+`
Jack
Hmm... yes I think I did mean * - you have to allow empty decimal part if people are typing it manually (original question), otherwise people cannot type decimals at all.
Nico Burns
Yeah, in this case you should since matching is done on a per character basis. Otherwise is just a choice (I don't like empty decimals for example :)
Jack
How would this work? If you check after each keystroke you could never enter a decimal point. ===> e.g Step 1: `5` - Step 2: `5.` *INVALID* so you could never enter, let's say `5.0`.
Peter Ajtai
Thanks, this looks like it'll do the trick, but I'm not sure how I can apply it to the textbox on the textbox before the characters appear. Any suggestion?
DaveDev
@Dave - It'd be quite complex. You'd have to intercept the keypress.... but imagine trying to accommodate copy paste or keeping a key down like that? very difficult
Peter Ajtai
A: 

You can use a plugin or another separate library to do form validation. An example: http://www.geektantra.com/2009/09/jquery-live-form-validation/

Regular expressions would also work if you wanted to handle this manually.

Andrew M
+1  A: 

Seems like a work for regular expressions:

var x = '0.00';
var y = '0.000.00';
x.match(/^[0-9]+\.*[0-9]*$/); 
y.match(/^[0-9]+\.*[0-9]*$/); // evaluates to null
Paulo Scardine
If you want to test if a string matches a regex you can also use `.test()`
Peter Ajtai
+1  A: 

It's a little tricky, since you want to make sure you can enter all numbers left to right, but something like this:

$("input").keyup(function() {       
    this.value = this.value.match(/[-+]?[0-9]*\.?[0-9]*/);
});

Try it out with this jsFiddle

Note how I'm checking the number from left to right. This means that + must be valid. Also 5. must be valid, or you could never enter 5.0 or +5.

Now the above has some major issue (try the arrow keys).

Here's a slightly more elegant solution that accommodates a default value as well:

$(function() {                      // <== DOC ready

    var prev="";                    // Initial value to replace default text with

    $("input").click(function () {  // Include a select on click
        $(this).select();           // if you have a default value
    });

    $("input").keyup(function() {  

        if(/^[-+]?[0-9]*\.?[0-9]*$/.test(this.value)) // If number....
            prev = this.value;                        // store it as the fallback
        else
            this.value = prev;                        // else go to fallback
    });
});

Try it out with this jsFiddle

Example HTML for the above:

<input type="text" value="Enter only a number" />

Note how when you use .test() you have to test from the beginning ^ to the end $.

Peter Ajtai
A: 

I'm using this plugin for my projects: http://www.texotela.co.uk/code/jquery/numeric/

it's simple but have some bugs with negative values, anyway it works great for a simple use!

you can you use it like so:

$("input.numericInput").numeric();
Gab