how to calculate a number in 2 decimals behind the dot - javascript

This is my form:
<input type="text" class="form-control amount" value="" placeholder="amount" />
<input type="hidden" class="price" value="3.30" />
<input type="text" class="form-control total" value="" disabled />
My js:
$('.amount').on('keyup', function (e) {
e.preventDefault();
var amount = $('.amount').val();
var total = Number(amount) * Number($('.price').val());
$('.total').val(total);
});
If i fill in an amount of 3, the result in input with class total shows me: 9.899999999999999 instead of 19.80. (3 * 3.30 is exactly 9.90).
Can someone explain me why the result is so many chars behind the dot?
I know i can reduce the result in 2 decimals with .toFixed(2) but that doesn't explain for me why a value which is exactly 9.90 changes into 9.899999999999999
Fiddle

This is because the way float numbers are stored as binary digits. To enable a wide rage of numbers and still maintain a reasonable size in memory for each number, the precision of results is sacrificed a bit. You can read more about here https://stackoverflow.com/a/588014/3807365

This happens due to the how floating point arithmetic works. In a few words, the floating number is not represented internally as-is, so when the language goes back and forth to display it, there can be some precision issues (such as the one you are facing). See the link for more details.
In summary, as you seem to be handling currency calculations, your best option is to use, instead of float, a specific datatype such as currency.js:
$('.amount').on('keyup', function (e) {
e.preventDefault();
var amount = $('.amount').val();
var total = currency(amount).multiply(currency($('.price').val()));
$('.total').val(total);
});
<script src="https://cdn.jsdelivr.net/npm/currency.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<input type="text" class="form-control amount" value="" placeholder="amount" />
<input type="hidden" class="price" value="3.30" />
<input type="text" class="form-control total" value="" disabled />
There are many libs for that, another one is dinero.js.

Related

Why am I seeing an unexpected value returned from toFixed()?

So there is an input field where I enter my digits. And in one of the field is specified for decimal digits(after coma). So for example if I enter 2, the amount of after coma digits should be 2 in all fields. I used math round + toFixed function to do that but for some reason it doesnt give me the desired output, even thought a program reads decimal value
Please help me understand why!
function convertToOthers(convertFrom, value, dec) {
if (parseFloat(dec.value)) {
switch (convertFrom) {
case "mm":
mmToOther(parseFloat(Math.round((value * 1000) / 10 / 100)).toFixed(parseFloat(dec.value)));
break;
}
}
}
<label for="mm">Milimeters - mm</label>
<div>
<input type="text" class="fname" id="mm" value="" name="inputNumber" oninput="convertToOthers('mm', this.value, dec)" /> <button class="buttonPic" onclick="copyFunction('mm')"></button><br><br>
</div>
<label for="dec">Decimal digits</label><br>
<div>
<input type="text" class="fname decimal" id="dec" value=""><br><br>
</div>
toFixed()
I have used toFixed() to fix the number to decimal places.
The toFixed() method formats a number using fixed-point notation.
Syntax
toFixed(digits)
Return value
A string representing the given number using fixed-point notation.
Demostration:
function mmToOther(x) {console.log("eval", x)}
function convertToOthers(convertFrom, value, dec){
if(parseFloat(dec.value)){
switch(convertFrom){
case "mm" : mmToOther(
Number.parseFloat(value).toFixed(parseFloat(dec.value))
);
break;
}
}
}
<label for="mm">Milimeters - mm</label>
<div>
<input
type="text"
class="fname"
id="mm"
value=""
name="inputNumber"
oninput="convertToOthers('mm', this.value, dec)"
>
<button class = "buttonPic" onclick = "copyFunction('mm')" >COPY</button>
<br>
<br>
</div>
<label for="dec">Decimal digits</label><br>
<div>
<input type="text" class="fname decimal" id="dec" value="" ><br><br>
</div>

Comma separated step for number input box

I can specify the 'step' for thousand increments when a user inputs a number. But why I cannot write '1,000' instead of '1000' for the increment to happen with the comma separation for thousands? How to do this?
<div class="input"><label for="salary">Salary</label>
<input class='inp_cont' id="salary" name="salary" placeholder="Enter your salary" step="1000" min="0" required="" type="number"></div>
It cannot be done if you want to stick to the type="number", because:
As Chrome reports:
The value must match to the following regular expression: -?(\d+|\d+.\d+|.\d+)([eE][-+]?\d+)?
As specification mentions:
value = floating-point number
Follow the above link to see that spec doesn't mention use of comma at all.
If you want to switch to type="text":
document.getElementById('salary').addEventListener('input', event =>
event.target.value = (parseInt(event.target.value.replace(/[^\d]+/gi, '')) || 0).toLocaleString('en-US')
);
<div class="input">
<label for="salary">Salary</label>
<input class='inp_cont' id="salary" pattern="^[\d,]+$" name="salary" placeholder="Enter your salary" required="" type="text">
</div>

Add (or multiply, subtract or divide) one var to another in JS/jQuery

Sincere apologies if this has been asked and answered elsewhere, I struggled with finding accurate search terms for this.
Working in jQuery I have a var called total. I need to add the value of other vars to total. All the vars in question have numerical values.
This is what I've tried:
var total = total+rocketspend;
$(".totalamount").html(total);
and
var newtotal = total+rocketspend;
var total = newtotal;
$(".totalamount").html(total);
Both have resulted in .totalamount being emptied and replaced with nothing. I have theories around why this might be going wrong - it could be that in the first example a var isn't allowed to be self defining, and it could be that in in the second example the browser attempts to define both newtotal and total at the same time, ending in mystery. Or it could be something else entirely. The rocketspend var works fine on its own, as does total before the attempted addition.
Thoughts?
You only need to use var when you first define a variable. It looks like you're trying to access a variable that already exists. Example:
var total = 0;
var rocketspend = 10;
total = total + rocketspend;
$(".totalamount").html(total);
Additionally, try checking your console for any errors. In most browsers, you can right click and inspect an element or click Ctrl + Shift + I and clicking on the Console tab. You can use Ctrl + Shift + K in Firefox.
You are using jQuery and have referenced an element (i.e. .totalamount) so assuming you are using normal webpage (i.e. HTML, CSS, JS/jQ etc..), this Snippet has 2 <forms>. The first one uses only JavaScript and HTML5. The second form uses jQuery and HTML5.
When using form fields such as <input>, the value you type in them will be a string (i.e. text) value. So when "3" is typed in, the <input> will treat it as text not a real number value. So convert the string to a number, use parseFloat(), parseInt(), or Number().
To get <input> values use .val() (jQuery) or .value (JavaScript).
SNIPPET
$('#calc1').on('input', function() {
var rocket1 = $('#rocket1').val();
var sub1 = $('#sub1').val();
var total1 = parseFloat(sub1) + parseFloat(rocket1);
$("#total1").val(total1);
});
input {width: 8ex;}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<p>Using only plain JavaScript and HTML5 form fields</p>
<form id="calc" name="calc" oninput="total.value = parseFloat(sub.value, 10) + parseFloat(rocket.value, 10)">
<fieldset>
<legend>Rocket Expenditure</legend>
<label for="sub">
<b>Sub Total:</b>
<input type="number" id="sub" name="sub" value="0">
</label> +
<label for="rocket">
<b>Rocket:</b>
<input type="number" id="rocket" name="rocket" value="0">
</label>
<label>
<b>Total:</b>
<output name="total" for="sub rocket">0</output>
</label>
</fieldset>
</form>
<p>Using jQuery and HTML5 form fields</p>
<form id="calc1" name="calc1">
<fieldset>
<legend>Rocket Expenditure 1</legend>
<label for="sub1">
<b>Sub Total 1:</b>
<input type="number" id="sub1" name="sub1" value="0">
</label> +
<label for="rocket1">
<b>Rocket 1:</b>
<input type="number" id="rocket1" name="rocket1" value="0">
</label>
<label>
<b>Total 1:</b>
<output id="total1" name="total1" for="sub1 rocket1">0</output>
</label>
</fieldset>
</form>

Javascript - decimal format

Edit: this isn't a math or operators question (I don't think). This is a formatting or masking question.
Creating an order form. I have Javascript that tallies/totals each column and displays the quantity and column cost in two other fields. I would like for the column cost to be formatted with a decimal and 2 values after it, but can't seem to figure it out. .toFixed(2) doesn't seem to work (because it's a string?) and I'm wondering if it's because the quantity and cost fields are readonly?
I'm stuck.
//example of tallying one column
<input type="number" min="0" value="0" name="proA#x#" class="input-mini proA qty1 coffee total">
$(document).on("change", ".qty1", function() {
var sum = 0;
$(".qty1").each(function(){
sum += +$(this).val();
});
$(".total1").val(sum);
$(".cost1").val(sum*9.00);
});
//item tally
<input type="number" id="D1" name="D1" class="input-mini uneditable-input total1" placeholder="0" readonly>
//item cost
<input type="number" id="" name="" class="input-mini uneditable-input cost1" placeholder="x 9.00" readonly >
Thanks in advance!
I would do it this way
var sum = 0.00;
$(".qty1").each(function(){
sum += parseFloat($(this).val());
});
$(".cost1").val(sum.toFixed(2));

Get values from inputs, calculate them and show the result

I have these two text inputs:
<input type="text" value="" id="width" name="width" />
<input type="text" value="" id="height" name="height" />
And below there is:
<h1>Summ: xxxxxx</h1>
I want to replace xxxxx with the following math:
(width * height) / 2
Whenever I type a new value at width or height inputs, the Summ should change realtime.
Is this possible at all?
Thank you.
You have multiple options to do that. There are many technologies frameworks, libraries, and ways to do it.
In my case (as I'm more familiar with this), the easier would be to use JQuery like this.
$('#width, #height').on('input', function(){
var width = $('#width').val();
var height = $('#height').val();
if (width != "" && height != "")
$('#result').text(width*height/2);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<input type="number" value="" id="width" name="width" />
<input type="number" value="" id="height" name="height" />
<h1>Result: <span id='result'>0</span></h1>
Obs: I changed your input fields to numeric type, so the user won't enter non-numeric data.
Quick fix:
<input type="text" value="" id="width" name="width" />
<input type="text" value="" id="height" name="height" />
<h1 class="calc"></h1>
And:
$('#width, #height').on('input', function () {
var widthInput = $('#width').val()
var heightInput = $('#height').val()
var result = widthInput * heightInput / 2
$('.calc').text(result)
})
You might wanna put a placeholder value like 1 for each field so it doesn't begin calculating with a 0. Also, it's spelled "sum" and not "summ", and it's not a sum anyway.
Fiddle here.
The main pieces of the problem are:
How do I get the value of an input box?
How do I execute code whenever input changes?
How do I set the text of an element?
The relevant functions are val(), change(), and text() respectively. The examples in the documentation should help you figure out how to piece it all together.

Categories

Resources