Laxmi Raghu
Laxmi Raghu

Reputation: 115

RegEx in Javascript to allow negative decimal input to a text field

I have a requirement wherein i need to allow plus/minus sign in the beginning followed by a decimal number which allows only one dot in it in a text field input in html.

Bascially the text field should allow normal integer numbers and decimal numbers and also negative integer and negative decimal numbers. The plus and minus sign should be allowed only in the beginning (first character) and it's optional. Also should allow any number of decimal places (ex: -12.12345 etc) but only one decimal (dot) in the entry.

Digits allowed are: 1, + 1, -1, .1, +1.1, -1.1, -.12, +.12, 123.4456, -123.345, +123.345 etc

Any help is highly appreciated.

I'm using below regex for the above requirement.

var integerOnly = /[\+\-0-9\.]/g;

and below script (which i obtained from some other thread with slight modification) to validate it .

function restrictInput(myfield, e, restrictionType, checkdot){
    if (!e) var e = window.event
    if (e.keyCode) code = e.keyCode;
    else if (e.which) code = e.which;
    var character = String.fromCharCode(code);
    alert("1 " + character);
    // if user pressed esc... remove focus from field...
    if (code==27) { this.blur(); return false; }
    //alert("2");
    // ignore if the user presses other keys
    // strange because code: 39 is the down key AND ' key...
    // and DEL also equals .
    if (!e.ctrlKey && code!=9 && code!=8 && code!=36 && code!=37 && code!=38 && (code!=39 || (code==39 && character=="'")) && code!=40) {
        alert("3");
        if (character.match(restrictionType)) {
            alert("4");
            if(checkdot == "checkdot" & '-' != character & '+' != character){
                alert("5");
                return !isNaN((myfield.value.toString()==''? '0':myfield.value.toString())+character );
            } else {
                return true;
            }
        } else {
            return false;
        }
    }
}

Here is how the script is called.

<input type="text" id="db" width="3" value=""   onkeypress="return restrictInput(this, event, integerOnly, 'checkdot');"/>

It works fine except for few cases like:

  1. It allows +/- any place any number of times. My requirement is to allow only at the beginning.

I tried to modify the regex as below.

var integerOnly = /[\+\-]?[0-9\.]/g;

In that case, it doesn't match the expression. It doesn't reach alert 4.

One thing is it allows only one decimal places and not more than one.

Can someone help me to modify my regular expression so as to allow only +/- in the beginning and only once.

Thank you.

Upvotes: 2

Views: 4883

Answers (4)

Laxmi Raghu
Laxmi Raghu

Reputation: 115

I took 'niksvp' script and modified a bit to meet my requirement.

The below script works for all types of +/- decimal numbers. ex: 1.1, +1.1, -1.1, .1, -.1, +.1, 1, -1, +1, 123.345, +123.345, -123.345 etc

function isNumber(myfield, e) {
if (!e) var e = window.event
    if (e.keyCode) code = e.keyCode;
    else if (e.which) code = e.which;
    var character = String.fromCharCode(code);

    var n = myfield.value.toString()==''? '0':myfield.value.toString();
    // this is required to allow numbers of this format
    // -1.1, + 1.1, .1, -.1, +.1 etc
    if(n == '-' | n == '+' | n== '.') {
        n +=0;
    }

    if(n.length > 1) {
        n = n.toString() + character;
    }

   return !isNaN(parseFloat(n)) && isFinite(n);
}

Thanks to all for your help.

Upvotes: 0

Ya Zhuang
Ya Zhuang

Reputation: 4660

var test_ary = ['1', '+1', '-1', '.1', '+1.1', '-1.1', '-.12', '+.12', '123.4456', '-123.345', '+123.345'];

var reg = /^[\+\-]?(?:\.?\d+|\d+\.?\d+)$/;

var i;


for ( i = 0; i < test_ary.length; i = i + 1) {
    console.log(reg.test(test_ary[i]));
}

you can also try this, with test case :)

Upvotes: 1

niksvp
niksvp

Reputation: 5563

Instead of playing with regex, validate your text using isNumber function as follows

function isNumber(n) {
  return !isNaN(parseFloat(n)) && isFinite(n);
}

Upvotes: 4

Guffa
Guffa

Reputation: 700362

I think that you want something like this:

^[-+]?(\d+\.?|\d*\.\d+)$

As the digits before the decimal separator or the digits after are optional (e.g. 1. or .1) but noth both, you need to handle the cases separately.

Upvotes: 1

Related Questions