When I pull the values I want to multiply, they're strings. So I pull them, parse them as floats (to preserve the decimal places), and multiply them together.
LineTaxRate = parseFloat(myRate) * parseFloat(myQuantity) * parseFloat(myTaxRateRound);
This has worked for 99% of my invoices but I discovered one very odd problem.
When it multiplied: 78 * 7 * 0.0725
When you normally do the math in a calculator its: 39.585
When all is said and done, I take that number and round it using .toFixed(2)
I tried Math.round() the total but I still get the same number.
I have thought of rounding the number to 3 decimals then two, but that seems hacky to me.
I have searched everywhere and all I see is people mention parseFloat loses its precision, and to use .toFixed, however in the example above, that doesn't help.
Here is my test script i made to recreate the issue:
<script> var num1 = parseFloat("78"); var num2 = parseFloat("7"); var num3 = parseFloat("0.0725"); var myTotal = num1 * num2 * num3; var result = Math.round(myTotal*100)/100 alert(myTotal); alert(myTotal.toFixed(2)); alert(result); </script>
edit: ooh! you can do 78 * 7 * 725 and then divide by 10000, or to be even more precise just put the decimal point in the right place. Basically represent the tax rate as something other than a tiny fraction. Less convenient but it'll probably take care of your multiplication errors.
You might find the Accounting.js library useful for this. It has an "improved" toFixed() method.
new Decimal(78).mul(7).mul(0.0725) returns as expected 39.585
©2020 All rights reserved.