JavaScript regex auto commas with decimals - javascript

I'm using the following JavaScript + Regex to auto add commas to a user input as they type:
$('input.number').keyup(function(event) {
// skip for arrow keys
if(event.which >= 37 && event.which <= 40) return;
// format number
$(this).val(function(index, value) {
return value
.replace(/[^-\d.]/g, "")
.replace(/\B(?=(\d{3})+(?!\d))/g, ",")
;
});
});
This works great, but it does not work for decimals. It adds commas to the decimals, which I don't want.
I could update the code to do a check to see if there are commas after the decimal. However, I think there may be a more elegant solution with Regex.
$('input.number').keyup(function(event) {
// skip for arrow keys
if(event.which >= 37 && event.which <= 40) return;
// format number
$(this).val(function(index, value) {
var num = value
.replace(/[^-\d.]/g, "")
.replace(/\B(?=(\d{3})+(?!\d))/g, ",");
var numSplit = num.split('.');
if(numSplit.length > 1){
num = numSplit[0] + '.' + numSplit[1].replace(/,/g, "");
}
return num;
});
});
I've tried adding a check to first see if a . exists. But I did not write it correctly.
\B(?=[^.](\d{3})+(?!\d))
Is there a better way to do this with regex?
https://codepen.io/anon/pen/gNOgMm

Apply Regex only to the whole number
$('input.number').keyup(function(event) {
// skip for arrow keys
if (event.which >= 37 && event.which <= 40) return;
// format number
$(this).val(function(index, value) {
var num = value
.replace(/[^-\d.]/g, "")
var numSplit = num.split('.');
if (numSplit.length > 1) {
num = numSplit[0]
.replace(/\B(?=(\d{3})+(?!\d))/g, ",") + '.' + numSplit[1].replace(/,/, "");
} else {
num = num.replace(/\B(?=(\d{3})+(?!\d))/g, ",")
}
return num;
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<input class="number">
Shorter Version
$('input.number').keyup(function(event) {
// skip for arrow keys
if (event.which >= 37 && event.which <= 40) return;
// format number
$(this).val(function(index, value) {
var num = value
.replace(/[^-\d.]/g, "")
.replace(/^\.+/g, "")
.replace(/\./, "x").replace(/\./g, "").replace(/x/, ".")
return (/^\d+\.\d+$/.test(num))
? num.replace(/(\d)(?=(\d{3})+(?:\.\d+)$)/g, "$1,")
: num.replace(/\B(?=(\d{3})+(?!\d))/g, ",")
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.0/jquery.min.js"></script>
<input class="number">

So, with a simple replace callback you can match the decimal part
then just return it, or match the assertion for a thousands place
then return ,.
No need to split, it just makes it more complicated.
Since you're using regex, do it all with regex.
The regex expanded:
( \. \d* ) # (1), Decimal part
| # or,
\B # Thousands part
(?=
(?: \d{3} )+
(?! \d )
)
var input = "122341234.188874";
input = input.replace (/[^-\d.]/g, "" );
input = input.replace (/(\.\d*)|\B(?=(?:\d{3})+(?!\d))/g,
function( m, g1 ) // match, group 1
{
if ( g1 > "" )
return g1;
else
return ",";
}
);
console.log(input);
Another thing you may want to consider is to validate the
form after stripping invalid characters.
I believe you could do that with a
replace (/^(?:.*?(-?(?:\d+(?:\.\d*)?|\.\d+))|).*$/g, "$1" );

Related

How to sanitize (digits and hyphen only) and auto-format (hyphen and leading zeros insertion) a text input value while typing and/or pasting text?

There are similar questions on SO, but mine is a bit unique. I want to limit an input text field to 9 characters in length (currently solved with maxlength attribute), only allow typing in numeric values and the hyphen character. Sort of handled with this code returning "True":
/^\d*\-?\d*$/.test(value)
Where I'm stuck is, I want the input text field to auto-format the value as the user types in the format:
12345-123
Where it's 5 digits (may have leading zeros or not depending on how user inputs it), followed by a hyphen, then always 3 digits. I'd like it to pad the first 5 with zeros if user enters something like "123-495" manually, so it would become "00123-495".
I'm not sure how to add in the auto-zero padding, or placement of the hyphen automatically.
Not opposed to using jQuery, but would prefer vanilla.
EDIT: Thought it might be useful to add. This is for an access card number entry box. So value will always be a positive number, and will always have 3 digits after the single hyphen. The card number will always be 5-digits in length, but again, may be padded with zeros to make it that length. Ideal output should always be "xxxxx-xxx".
EDIT 2: This seems to work, but there's an issue where user can enter non-numeric characters at first and after the 1st entry, only then does it clear it out. It also doesn't seem to let me hit backspace past the hyphen... Is there a way to prevent it from allowing alpha characters completely?
// Restricts input for the given textbox to the given inputFilter function.
function setInputFilter(textbox, inputFilter) {
["input", "keydown", "keyup", "mousedown", "mouseup", "select", "contextmenu", "drop"].forEach(function(event) {
textbox.addEventListener(event, function() {
if (inputFilter(this.value)) {
// Current value
new_val = '';
if (this.value.includes('-') && this.value.slice(this.value.indexOf('-')).length == 4) {
console.log("Value not hyphenated yet");
pad_needed = 5 - this.value.indexOf('-');
console.log('Pad needed: ' + pad_needed);
new_val = this.value.padStart(9, '0');
this.value = new_val;
} else if (this.value.length >= 5 && this.value.includes('-') && this.value.slice(this.value.indexOf('-')).length == 4) {
if (this.value.slice(5, 1) == '-') {
// Already a hyphen added, just add rest of numbers
new_val = this.value.slice(0, 6) + this.value.slice(6);
} else {
// Needs hyphen added
new_val = this.value.slice(0, 5) + '-' + this.value.slice(6);
}
this.value = new_val;
} else if (this.value.length >= 5 && !this.value.includes('-')) {
// Needs hyphen added
new_val = this.value.slice(0, 5) + '-' + this.value.slice(6);
this.value = new_val;
}
this.oldValue = this.value;
this.oldSelectionStart = this.selectionStart;
this.oldSelectionEnd = this.selectionEnd;
} else if (this.hasOwnProperty("oldValue")) {
this.value = this.oldValue;
this.setSelectionRange(this.oldSelectionStart, this.oldSelectionEnd);
} else {
this.value = "";
}
});
});
}
setInputFilter(document.getElementById("card-number"), function(value) {
return /^\d*\-?\d*$/.test(value); // Allow digits and '-' only
});
function getSanitizedInputValue(value) {
value = value
.trim()
.replace(/^[-]+/, '')
.replace(/[-]+/, '-');
let [
first,
...rest
] = (value.match(/[-\d]+/g) ?? [])
.join('')
.split('-')
let joiner = '';
if (first.length >= 6) {
joiner = '-';
rest.unshift(first.slice(5));
first = first.slice(0, 5);
} else if (rest.length >= 1) {
joiner = '-';
first = first.padStart(5, '0');
}
return [
first,
rest.join(''),
]
.join(joiner)
.slice(0,9);
}
function handleInput({ currentTarget: control }) {
const { value: recentValue, selectionStart, selectionEnd } = control;
const regXHasHyphen = /-/;
const sanitizedValue = getSanitizedInputValue(recentValue);
const sanitizedLength = sanitizedValue.length;
const recentLength = recentValue.length;
const positionDelta = (
(recentLength <= 5) &&
(sanitizedLength >= 6) &&
(sanitizedLength - recentLength)
) || (
!regXHasHyphen.test(recentValue) &&
regXHasHyphen.test(sanitizedValue) &&
1
) || 0;
control.value = sanitizedValue;
control.selectionStart =
Math.min(sanitizedLength, (selectionStart + positionDelta));
control.selectionEnd =
Math.min(sanitizedLength, (selectionEnd + positionDelta));
}
document
.querySelector('[type="text"]')
.addEventListener('input', handleInput);
<input type="text" maxlength="9" />

what are key values for special characters?

function alphaOnly(event) {
var key = event.keyCode;
return ((key >= 8 && key <= 47) || (key >= 65 && key <= 222));
};
My function is not able to print # # $ % & ! * ( )
I could not find key codes for the above symbols. Please help me to accept these characters.
You can use regular expression instead on checking ascii values :
<script type="text/javascript">
function alphaOnly() {
var isValid = false;
var regex = /^[a-zA-Z%*#]*$/;
isValid = regex.test($("#field").val());
return isValid;
}
</script>

Can't delete dynamically added colon

I need a function that will add the colon (:) after you type two numbers in input and I found this solution here on StackOverflow as well which is what I need. It add colon after typed second number and won't let u add more than 4 numbers.
However, there is an issue that I can't understand and solve. I need to be able to delete all numbers, but it won't let me. I can delete only last two, and you can't delete colon.
Here is the current code:
var time = document.getElementsByClassName('time');
for (var i = 0; i < time.length; i++) {
time[i].addEventListener('keyup', function (e) {
var reg = /[0-9]/;
if (this.value.length == 2 && reg.test(this.value)) this.value = this.value + ":"; //Add colon if string length > 2 and string is a number
if (this.value.length > 5) this.value = this.value.substr(0, this.value.length - 1); //Delete the last digit if string length > 5
});
};
https://jsfiddle.net/bubxm7pe/
You can add condition for backspace with e.keyCode
It works here
if (e.keyCode != 8)
{
var reg = /[0-9]/;
if (this.value.length == 2 && reg.test(this.value)) this.value = this.value + ":"; //Add colon if string length > 2 and string is a number
if (this.value.length > 5) this.value = this.value.substr(0, this.value.length - 1); //Delete the last digit if string length > 5
}
Update: You can also restrict user with digits like following. It also works here
//called when key is pressed in textbox
$(".time").keypress(function (e) {
//if the letter is not digit then don't type anything
if (e.which != 8 && e.which != 0 && (e.which < 48 || e.which > 57)) {
return false;
}
else
{
var reg = /[0-9]/;
if (this.value.length == 2 && reg.test(this.value)) this.value = this.value + ":"; //Add colon if string length > 2 and string is a number
if (this.value.length > 4) this.value = this.value.substr(0, this.value.length - 1); //Delete the last digit if string length > 5
}
});
Rather than check for delete or backspace you could check if the key pressed is a number:
if (keycode >= 48 && keycode <= 57) {
if (this.value.length == 2 && reg.test(this.value)) this.value = this.value + ":"; //Add colon if string length > 2 and string is a number
if (this.value.length > 5) this.value = this.value.substr(0, this.value.length - 1); //Delete the last digit if string length > 5
}
https://jsfiddle.net/6jbaayqd/
As you are already inclined to use regex, then why not use it for formatting the time in the input field - see demo below:
document.getElementsByClassName('time')[0].addEventListener('keyup', function(e) {
this.value = this.value
.replace(/[^\d]/g, '') // allow only digits
.replace(/^([\d]{4})\d+$/g, '$1') // restrict to 4 chars
.replace(/\B(?=(\d{2})+(?!\d{1}))/g, ":"); // place the colon
});
<input class="time" />

javascript limit on positive and negative number with delimiter comma based onkeyup and onkeypress

Today i have problem in delimiting number for negative and positive number. For example, i have a textbox to insert my number and the result after write the number. Suddenly the number is separated with comma delimiter like this either the number is positive or negative
eg : 1000 -> 1,000
-1000 -> -1,000
-1000.12 -> -1,000.12
-0.00001 -> -0.00001
How to achieve this using javascript, what i know is using onkeypress and onkeyup. Thank you very much :)
This is not the best solution, but you can implement this according to your need.
var msg = document.getElementById('myInputBox'),
numberPattern = /^[0-9]+$/;
msg.addEventListener('keyup', function(e) {
msg.value = getFormattedData(msg.value);
});
function checkNumeric(str) {
return str.replace(/\,/g, '');
}
Number.prototype.format = function() {
return this.toString().replace(/(\d)(?=(\d{3})+(?!\d))/g, "$1,");
};
function getFormattedData(num) {
var i = checkNumeric(num),
isNegative = checkNumeric(num) < 0,
val;
if (num.indexOf('.') > -1) {
return num;
}
else if (num[num.length - 1] === ',') {
return num;
}
else if(i.length < 3) {
return i;
}else {
val = Number(i.replace(/[^\d]+/g, ''));
}
return (isNegative ? '-' : '') + val.format();
}
<input type="text" id='myInputBox' value="" />

replace number and symbol with jquery/javascript

Does anyone know how can I replace the number and symbol (excluding dash and single quote)?
Example:
if I have a string "ABDHN'S-J34H##$";
How can I replace the number and symbol to empty and return me value "ABDHN'S-JH" ?
I have the following code to replay all the char and symbol to empty and only return me number
$(".test").keyup(function (e) {
orgValue = $(".test").val();
if (e.which != 37 && e.which != 39 && e.which != 8 && e.which != 46) {
newValue = orgValue.replace(/[^\d.]/g, "");
$(".test").val(newValue);
}
});
You should allow only letters, dash and single quotes, like this:
newValue = orgValue.replace(/[^a-zA-Z'-]/g, "");
Anything else will be replaced by "".
You can use this regex:
string.replace(/^[a-zA-Z'-]+$/, '')
The caret ^ inside a character class [] will negate the match. This regex will convert all characters other than a-z, A-Z, single quote and hyphen to empty
You could replace symbols by skipping them through keycode value on the keyboard.
Link for keycode values for reglar keyboard:
http://www.w3.org/2002/09/tests/keys.html
$("#your control").bind("keydown keyup", doItPlease);
function doItPlease(e)
{
// First 2 Ifs are for numbers for num pad and alpha pad numbers
if (e.which < 106 && e.which > 95)
{
return false; // replace your values or return false
}
else if (e.which < 58 && e.which > 47)
{
// replace your values or return false
} else {
var mycharacters = [8, 9, 33, 34, 35 // get your coders from above link];
for (var i = 0; i < mycharacters.length; i++) {
if (e.which == mycharacters[i]) {
// replace your characters or just
// return false; will cancel the key down and wont even allow it
}
e.preventDefault();
}
"ABDHN'S-J34H##$".replace(/[^\-'\w]/g, '')
"ABDHN'S-J34H##$".replace(/[0-9]|[\'##$]/g, "");

Categories