I have a text box where the value is the result of a calculation carried out in jQuery. What I would like to do, using jQuery, is to display brackets around the number in the text box if the number is negative.
The number may be used again later so I would then have to remove the brackets so further calculations could be carried out.
Any ideas as to how I could implement this?
Thanks
Zaps
function FormatTextBox(id) {
var txtBox = $(id).val();
//strip bracket to get the number only
txtBox = txtBox.replace("[", "").replace("]", "");
var val = parseFloat(txtBox);
if (val < 0) {
txtBox.val("[" + val + "]");
} else {
txtBox.val(val);
}
return val;
}
First, store your calculation in a variable. You shouldn't be using the DOM to store data (in most cases). This basically eliminates your problem.
Number.prototype.bracketed = function() {
if(this < 0) {
return '[' + -this + ']';
} else {
return '' + this;
}
};
var result = do_calculation();
myTextBox.value = result.bracketed();
// result still holds the original Number value.
If you really want to store the data as the .value of the text input, you can make an unbracketed function as well:
String.prototype.unbracketed = function() {
var parts = this.match(/^\[([0-9]+)\]$|^([0-9]+)$/); // [number] or number
if(parts[1]) { // [number]
return -parseInt(parts[1], 10);
}
if(parts[2]) { // number
return parseInt(parts[2], 10);
}
return NaN;
};
Assuming you might have multiple fields (and you don't want the negative sign):
jQuery('input').each(function(){
if(jQuery(this).val() < 0 ){
jQuery(this).val('['+-1*jQuery(this).val()+']');
}
}
)
Then when you grab the value again, just strip the brackets and multiply by -1 to make it negative.
EDIT:
You can also use jQuery('input').data() to store the original number so you don't have to parse it again. (read more: http://api.jquery.com/data/ )
Related
My goal is to edit the string (which has an email) to mask the first part, like say the email is johndoe#abc.com then I should output j*****e#abc.com.
var maskPII = function(S) {
var ans = "";
if(S.includes("#")){
S = S.toLowerCase();
var parts = S.split("#");
var first = parts[0];
for(var i=0;i<parts[0].length;i++){
if(i!=0 && i!=parts[0].length - 1)
first[i] = '*';
}
ans = first +"#" +parts[1];
}else{
}
return ans;
};
However in my loop I can't change the characters to asterisks.
After execution I see value of first still same as parts[0] and has no asterisks, can some one explain why? Also, what would I need to do to modify the variable inside loop?
To answer your question... javascript allows you access values of a string using [] indexing.. but that is read only access... you cannot insert/replace values using that operator.
Ref: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String
When using bracket notation for character access,
attempting to delete or assign a value to these properties will not succeed.
The properties involved are neither writable nor configurable.
(See Object.defineProperty() for more information.)
You need to extract the values you want to keep from the existing string and build up a new string as noted in other answers...
Well, this's what you're looking for, and this will be the output j*****e#abc.com.
var ans = "";
var S = "johndoe#abc.com"; //example
S = S.toLowerCase();
var parts = S.split("#");
var first = "";
for(var i = 0; i < parts[0].length; i++){
if(i != 0 && i != parts[0].length - 1){
first += '*';
}else{
first += parts[0][i];
}
}
ans = first +"#"+ parts[1];
console.log(ans);
Here is the code with your approach:
var maskPII = function(S) {
var ans = "";
if(S.includes("#")){
S = S.toLowerCase();
var parts = S.split("#");
var first = parts[0][0];
for(var i=0;i<parts[0].length;i++){
if(i!=0 && i!=parts[0].length - 1)
first += '*';
}
ans = first + parts[0][parts[0].length - 1] +"#" +parts[1];
}else{
}
return ans;
};
But if i were you i would use:
var mail = "johndoe#abc.com";
mail = mail.replace(/(?<=.)(.+?)(?=.#)/gi, '*'.repeat(mail.split('#')[0].length - 2));
console.log(mail);
You can use the bracket notation on a string (like an array) to get the character at a specific index, but you can't use this to change characters. So first[i] = '*' in your code wont do anything.
Strings in JavaScript are immutable. This means that if you want to change a string, a new string instance will be created. This also means that when you change a string in a for-loop, it can impact performance. (Although in this case the difference wont be noticeable.
)
I would use this code:
function maskPII(str) {
const indexOfAt = str.indexOf('#');
if (indexOfAt <= 2) {
return str;
}
return str[0] + '*'.repeat(indexOfAt - 2) + str.substring(indexOfAt - 1);
}
const email = 'johndoe#abc.com';
console.log(email);
console.log(maskPII(email));
It will look for the index of the # sign. If the index is less or equal than 2, (when not found the index will be -1) it will return the original string.
Otherwise it will get the first character, calculate the amount of asterisks needed (index of the # sign -2) and repeat those and then add the rest of the original string.
I have simple code that will replace the characters in a string with '*' and only displays the last 4 characters of the string. Example:
string = 424242424242
Should become:
********4242
The code that does that is this:
var str = $('.cc').val();
var trailingCharsIntactCount = 4;
str = new Array(str.length - trailingCharsIntactCount + 1).join('*') + str.slice( -trailingCharsIntactCount);
$('.cc').val(str);
Now, I need to reverse that when the users focus on an input field.
This is a working fiddle:
https://jsfiddle.net/s66k9x1s/1/
Basically, I need to show/hide the input's value the same way I demonstrated in my fiddle.
Could someone please advice on how I can achieve this?
The string replacement cannot be reversed from thin air,
you need to save the original value somewhere.
You could use jQuery's .data(), for example.
Store the original value with .data('value', str),
and when the field receives the focus,
restore it from .data('value').
function getMaskedValue(str) {
var trailingCharsIntactCount = 4;
return new Array(str.length - trailingCharsIntactCount + 1).join('*') + str.slice(-trailingCharsIntactCount);
}
var $cc = $('.cc');
var str = $cc.val();
$cc.data('value', str);
$cc
.val(getMaskedValue(str));
.focus(function() {
$(this).val($(this).data('value'));
});
And as #aaron pointed out,
after focus is lost, you also want to restore the masked value:
$cc
.focus(function() {
$(this).val($(this).data('value'));
})
.blur(function() {
str = $(this).val();
$(this).data('value', str);
$(this).val(getMaskedValue(str));
});
He is also right that you don't need .data(),
you could store the real value in a variable.
It will be good to hide it within a closure.
(See fiddle.)
(function() {
function getMaskedValue(s) {
var masklen = s.length - 4;
return s.substr(0, masklen).replace(/./g, '*') + s.substr(masklen);
}
var $cc = $('.cc');
var value = $cc.val();
$cc
.val(getMaskedValue(value))
.focus(function() {
$(this).val(value);
})
.blur(function() {
value = $(this).val();
$(this).val(getMaskedValue(value));
});
})();
I also simplified the implementation of computing the masked value,
which should perform better, eliminating array operations.
Leave the original value in str. Here's a clean and simple answer that includes re-hide on blur:
var cc = $('.cc');
var str;
var trailingCharsIntactCount = 4;
function getHiddenValue() {
str = cc.val();
return new Array(str.length - trailingCharsIntactCount + 1).join('*') + str.slice(-trailingCharsIntactCount);
}
cc.val(getHiddenValue());
cc.focus(function() { cc.val(str); });
cc.blur(function() { cc.val(getHiddenValue()); });
I need to validate some user input with javascript. I need to check that their entry (value) is of the correct type (type).
I need my regex pattern to make sure values only contain numbers and nothing else, except measurment types can also contain decimal points.
What is the correct way to do this? My way seems like it may be, but i am guessing. In any case, something is wrong with my regular expression patterns as it is throwing the error stated in the code comment.
Here is my code:
function validateInput(value, type) {
console.log(value);
if(type === "Integer"){
var patt = new RegExp("^\D", i);
}
else if(type === "Measurement"){
var patt = new RegExp("^\D", i); //Uncaught SyntaxError: Invalid flags supplied to RegExp constructor '2'
}
else{
return true;
}
if(patt.test(value)){
return false;
}
else{
return true;
}
}
function sendObs() {
RID = $("#oid").val();
console.log(RID);
var children = $("#abc").children();
var xmlString = "<root><rid>" + RID + "</rid>";
for(i=0; i < children.length; i++){
var value = children[i].children[0].value;
var type = children[i].children[0].id;
var validationResult = validateInput(value, type);
if(!validationResult){ //calling the validation method here
alert("invalid entry");
return;
}
var code = children[i].children[0].className;
xmlString += '<question><code>' + code + '</code><value>' + value + '</value></question>'
}
xmlString +='</root>'
console.log(xmlString);
data = $.parseXML(xmlString);
console.log(data);
//send it here
}
Instead of using regular expressions, you could just call parseInt() and parseFloat().
On top of converting your strings to workable numbers, both functions return NaN if the input is invalid.
number = parseFloat(string)
if (isNaN(number)) {
# `string` is invalid
}
I have a PDF form that I'm making that adds up 5 fields with javascript.. The script will add all the numbers,but if one field is left blank the total is all screwed up. If I go back and add a zero to the blank field everything works fine. How can I fix this.
this.getField("RUNTOTAL").value = this.getField("RUNRow1").value + this.getField("RUNRow2").value + this.getField("RUNRow3").value + this.getField("RUNRow4").value + this.getField("RUNRow5").value;
OK so I tried this and it doesn't work at all now. Maybe I missed something?
function isNumeric(n) {
return !isNaN(parseFloat(n)) && isFinite(n);
}
function getFieldValue(RUNRow1) {
var value = this.getField(RUNRow1).value;
return isNumeric(value) ? value : 0;
}
function getFieldValue(RUNRow2) {
var value = this.getField(RUNRow2).value;
return isNumeric(value) ? value : 0;
}
function getFieldValue(RUNRow3) {
var value = this.getField(RUNRow3).value;
return isNumeric(value) ? value : 0;
}
function getFieldValue(RUNRow4) {
var value = this.getField(RUNRow4).value;
return isNumeric(value) ? value : 0;
}
function getFieldValue(RUNRow5) {
var value = this.getField(RUNRow5).value;
return isNumeric(value) ? value : 0;
]
this.getField("RUNTOTAL").value = getFieldValue("RUNRow1") + getFieldValue("RUNRow2") + getFieldValue("RUNRow3") + getFieldValue("RUNRow4") + getFieldValue("RUNRow5");
This is a consequence of the loose typing of JavaScript. And it hits me every now and then. By default, JavaScript treats the empty string as string, and not as number 0, unless you persuade it to do so.
The simplest way would be multiplying every field value with 1 (which assumes that the fields do contain strings which can be converted to valid numbers).
Therefore, the code would look like this:
this.getField("RUNTOTAL").value = this.getField("RUNRow1").value*1 + this.getField("RUNRow2").value*1 + this.getField("RUNRow3").value*1 + this.getField("RUNRow4").value*1 + this.getField("RUNRow5").value*1;
In Javascript I have a number and I want to add comma to it when it's displayed as a string.
I can add comma to the number like this:
function numberWithCommas(value) {
return value.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
}
But I don't want to call a method on every number that we have to get this. I want to do something similar to this:
Number.prototype.toString = function(radix) {
return numberWithCommas(this);
}
So when I do the following, the right value will show up:
var num = 100000;
alert(num); // 100,000
Can't get the above to work. Any ideas?
What about creating a new number function?
Number.prototype.withCommas = function(){
return this.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
}
var n = 1234567;
alert( n.withCommas() );
http://jsfiddle.net/kyX8x/1/