I have a field on a form in Adobe that automatically sums the values from six other fields. The sum results in a decimal "." being placed so there are always 2 digits following.
The values in each of the six fields are typed in using a space to act as decimal place, as in "14 50" = $14.50 (see image).
The resulting sum is correct, but I'd like to add custom formatting that will replace the "." with a space, so that the sum in my example would read "87 00" rather than "87.00"
The javascript must be code that will work in the Adobe Pro custom format option for the field.
var num = 87.27;
var formatted;
if (num % 1 === 0) {
formatted = num.toString() +' 00';
} else {
formatted = num.toString().replace('.', ' ');
}
Related
I am having trouble adding blank spaces to align the decimals. I understand the logic but I can't put it into code.
for(var j in totals_array)
{
var amount = format_numeric_with_commas(totals_array[j].amount);
var currency = totals_array[j].currency;
if(j < 1)
{
costs_total.push(currency + " " + amount + "\x0A");
}
else
costs_total.push(currency + Array(0).join(" ") + amount + "\x0A");
}
totals_array holds a number of objects which looks like this.
{"currency":"AUD","amount":210543}
format_numeric_with_commas gives me the amount value in the appropriate format which is stored into the variable amount. While currency takes the currency of the value, i.e. GBP, USD, etc. What the if statement is for checks if it's the first index in the array. As I already sort the values with the highest at the top. So what I want is for the other values to align with the top number's decimal.
I take the currency type and value and push into a new array called costs_total. This is what it currently looks like.
Current layout:
How would I go about doing a loop to check how many spaces are needed for different lengths of currency values?
Why not do something like this instead? (some examples with actual text / numbers)
costs_total.push(String.Format("{0} {1,12:N}\x0A", "USD", 123456.0));
// "USD 123,456.00\n"
costs_total.push(String.Format("{0} {1,12:N}\x0A", "AUD", 123.0));
// "AUD 123.00\n"
costs_total.push(String.Format("{0} {1,12:N}\x0A", currency, amount));
You'd just need to find the number of digits in the largest number and set the width (12 in this case) appropriately.
I have a value fetched from the database, it's like:
4.5 which should be 4.500
0.01 which should be 0.010
11 which should be 11.000
so I used this piece of code
sprintf("%.3f",(double)$html['camp_cpc'])
But here arised another problem. If $html['camp_cpc'] = '4.5234', then also it displays 4.523 instead of original value 4.5234
Also for other values with larger decimal like 0.346513, its only showing up to 0.346.
How can I solve this problem in JavaScript also?
Floats 4.5 and 4.500 correspond to the same number, so they cannot (and should not) be used/stored in a way that preserves the different representation. If you need to preserve the original representation given by a user, you need to store this field as a list (string) and convert to a float whenever you need the float value
In Javascript at least, this is an implementation of what I think you want:
function getValue(x, points) {
var str = x.toString();
// Convert to string
var idx = str.indexOf(".");
// If the number is an integer
if(!~idx) return str + "." + "0".repeat(points);
// Get the tail of the number
var end = str.substr(idx+1);
// If the tail exceeds the number of decimal places, return the full string
if(end.length > points) return str;
// Otherwise return the int + the tail + required number of zeroes
return str.substr(0, idx) + "." + end.substr(0, points) + "0".repeat(points-end.length);
}
console.log(getValue(4.5, 3)); //4.500
console.log(getValue(0.01, 3)); //0.010
console.log(getValue(11, 3)); //11.000
Working demo (Makes use of ES6 String.repeat for demonstration purposes)
The important thing to note here is that this is string manipulation. Once you start to say "I want the number to look like..." it's no longer a number, it's what you want to show the user.
This takes your number, converts it to the string and pads the end of the string with the appropriate number of zeroes. If the decimal exceeds the number of places required the full number is returned.
In PHP, use %0.3f — and you don't need to cast as (double)
<?php
echo sprintf("%0.3f", 4.5); // "4.500"
echo sprintf("%0.3f", 4.5234); // "4.523"
If you want to display 4 decimal places, use %0.4f
echo sprintf("%0.4f", 4.5); // "4.5000"
echo sprintf("%0.4f", 4.5234); // "4.5234"
To do this in JavaScript
(4.5).toFixed(3); // "4.500"
It could look sth. like this:
var n = [4.5234, 0.5, 0.11, 456.45];
var temp_n;
for(var i = 0; i < n.length; i++) {
temp_n = String(n[i]).split(".");
if(temp_n[1] == null || temp_n[1].length < 3) {
n[i] = n[i].toFixed(3);
}
}
I have a number of prices on a page that arein 4 decimal places. Some products are priced in 4 decimal places, but some are only in 2.
At the moment our website is set to display in 4 decimal places for every product and I have to use javascript to trim down the prices on those products that aren't 2 decimal places.
So I have prices like so...
£0.1234
£1.1000
£10.9900
£100.0000
I have the following javascript which works fine for prices that have a number greater than 1 after the decimal point, but it fails on prices where there are just 0's after the decimal point...
$.each($("#mydiv"),function(){
var price = $(this).text().replace("£","");
var number = parseFloat(price);
var integerPart = number.toString().split(".")[0] == 0 ? 0: number.toString().split(".")[0].length;
var decimalPart = number.toString().split(".")[1].length;
if(decimalPart > 2){
$(this).text("£" + number.toPrecision(integerPart + decimalPart));
}else{
$(this).text("£" + number.toPrecision(integerPart + 2));
}
});
The ones it fails on are prices like £100.0000 - I would like the prices to appear as follows - no rounding...
£0.1234
£1.10
£10.99
£100.00
Just use a regexp to remove any trailing zeroes if the preceeding characters are the decimal period followed by another two digits:
$('.myClass').text(function(_, t) {
return t.replace(/(\.\d\d)00$/, '$1');
});
NB: you can't use duplicate element ID's, so your $.each call should be moot. If there really are multiple fields that this needs doing to, mark them with a class, not an ID. The .text call in the code above will automatically cope with multiple elements.
EDIT if you really can't upgrade your jQuery:
$('.myClass').each(function() {
var $this = $(this);
var text = $this.text();
text = text.replace(/(\.\d\d)00$/, '$1');
$this.text(text);
});
Additional to Alnitak's answer, I would highly recommend to store the prices of your store's items as integers (or maybe in your case longs), so you don't have to worry about imprecisions of double or float.
Because you have 4 decimal places the integers (or longs) can not represent pence, but 1/100 pence.
Example:
Price on website | price in database
-------------------------------------------
£0.1234 | 1234
£1.10 | 11000
£10.99 | 109900
£100.00 | 1000000
I need to validate a textbox field that will contain a range (separated by -). Following are the requirements:
Need to validate year & month ranges, and have values like 0.5 - 3.11 for denoting 5 months to 3 years and 11 months
The decimal places can be max 2 and 11 is max value in decimal place while 0 is minimum.
Both parts separated by hyphen -, may or may not include 1 blank space (only before and after hyphen).
The left part must always be less than right part.
Should validate values like:
1
2.3
2.3 - 4.6
2.3-4.6
2.4-2.1 is invalid
No negative required for the float values
I tried to generate some regex but the closest was:
(0|([1-9][0-9]{0,9}))(\.[0-9]{1,2})?(-)(0|([1-9][0-9]{0,9}))(\.[0-9]{1,2})?
but it can only validate values like 1.3-1.9 but does not compares the left and right part. And only a single digit value is also not validated.
You could do most of the validation with a regex, but checking that the first value is less than the second value would have to be done in code rather than a regex.
function isRangeStringValid(r) {
if (!r.match(/(0|[1-9]\d*)\.(\d|1[01]) ?- ?(0|[1-9]\d*)\.(\d|1[01])/)) {
return false;
}
var y1 = parseInt(RegExp.$1);
var m1 = parseInt(RegExp.$2);
var y2 = parseInt(RegExp.$3);
var m2 = parseInt(RegExp.$4);
return (y1<y2 || (y1==y2 && m1<m2));
}
yet another variant function with regexp for solution
function israngev(r){
var res = r.match(/^\d+$|^\d+\.(\d|1[01])$|^(\d+\.(\d|1[01])) ?- ?(\d+\.(\d|1[01]))$/);
return res!=null &&
(!(res[1]||res[2]||res[4]) ||
(res[1]!=null ||
(res[4]-res[2]>0)))}
First of all,
What am i doing ?
I have to set the limit of emails in our product in webpage.It's handled with the javascript for validation.It handles upto 8 digit numbers fine. But in our QA team enters the more than 17 digit number in the text box of other email field.It throw the negative message.What can i do ???
My sample code is:
if(form.otherEmails) {
if(validEmailArray.endsWith(',')){
var otherEmailLength = validEmailArray.substring(0,validEmailArray.length-1).split(",");
var setLimitOtherEmail = window.parent.document.getElementById('setLimitOtherEmail').value;
if(setLimitOtherEmail == '-1'){
form.otherEmails.value = otherEmailLength;
}
else if(otherEmailLength.length <= setLimitOtherEmail){
form.otherEmails.value = otherEmailLength;
}
else{
alert("More than "+setLimitOtherEmail+ " " +"Recipient emailIds not allowed in this section.\nIf you want to send it to more recipients, Please create a Bulk Contact Group.");
form.otherEmails.focus();
return false;
}
}
else
form.otherEmails.value = validEmailArray;
}
This is due to the limit being a string, and when a string is being compared to a number (length) the number is coerced into a string, not the other way around.
These are then compared lexicographically - and lexicographically "9" is more (>) than "19".
You need to use parseInt(setLimitOtherEmail, 10) to get the value as a number before comparing them.
Try parsing each of the numbers into Integers before performing any comparison operations on them.
var setLimitOtherEmail = parseInt(window.parent.document.getElementById('setLimitOtherEmail').value);
Other than that are you certain otherEmailLength is actually the number that you want? From the looks of it you are taking the substring of validEmail array and splitting it on "," but it doesn't look like you actually get the length of the array. Try adding .length to the end of the value of otherEmailLength.
var otherEmailLength = validEmailArray.substring(0,validEmailArray.length-1).split(",").length;