0

I'm trying to create a sample accounting system, the checkbox can be add to the total after it's checked and the input text is the amount of the money. but my result keep getting zero, I can't figure it out. Anyone can help me handle this problem? I've test that the length of total_ary is 0, I think that is the mainly problem

function Totalamount() {
  var input_cb = document.getElementsByName('cb');
  var amount = [];
  var total_ary = [];
  var total = 0;
  var price = [10, 20, 30];
  var i = 0;
  for (i = 0; i < input_cb.length; i++) {
    if (input_cb[i].checked) {
      amount.push(document.getElementsByName("amount").value); //get amounts of the products
    } else {
      amount.push(0); //If there is no input, add 0 to the array
    }
  }
  for (i = 0; i < total_ary.length; i++) {
    total_ary.push(parseInt(amount[i] * price[i])); // Add the products' total price to array
    total += parseInt(total_ary[i]); //Counting the total money
  }
  document.getElementById("result").innerHTML = "$" + 0;
  document.getElementById("result").innerHTML = "$" + total ;
}
<fieldset>
  <input type="checkbox" name="cb" checked>$10:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$20:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$30:<input type="text"  name="amount"><br>
</fieldset>
<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
  • Review your HTML. There are tons of syntax errors. Fix them first ! – Raptor Mar 12 '20 at 06:36
  • Hint: There's a major bug on this line: `amount.push( parseInt( document.getElementsByName( "amount" ).value ) )`. `getElementsByName` returns a collection of HTML elements, not a single element, so `.value` will throw an error. – Dai Mar 12 '20 at 06:38

6 Answers6

0

You do

document.getElementsByName("amount").value

but getElementsByName returns a collection, not an element.

You do

var total_ary = [];
// ... code that doesn't reference total_ary
for (i = 0; i < total_ary.length; i++) {
  total_ary.push(parseInt(amount[i] * price[i])); // Add the products' total price to array
  total += parseInt(total_ary[i]); //Counting the total money
}

But since the code in between doesn't reference total_ary, the total ends up being 0.

From a selected checkbox, you need to navigate to the associated input:

document.getElementsByName("amount")[i].value

since i is the cb index you're iterating over, the same i in the amount collection will refer to the input you need.

Or, more elegantly, just navigate to the next element in the DOM when a checkbox is checked, and take the number for each product's price from the DOM too. You can also select only the checked checkboxes immediately with a :checked selector, and attach the event listener using addEventListener (instead of an inline handler; inline handlers should be avoided)

document.querySelector('button').addEventListener('click', () => {
  let total = 0;
  for (const input of document.querySelectorAll('[name=cb]:checked')) {
    const price = input.nextSibling.textContent.match(/\d+/)[0];
    const amount = input.nextElementSibling.value;
    total += price * amount;
  }
  document.getElementById("result").innerHTML = total + "元";
});
<fieldset>
  <input type="checkbox" name="cb" checked>$10:<input><br>
  <input type="checkbox" name="cb" checked>$20:<input><br>
  <input type="checkbox" name="cb" checked>$30:<input><br>
</fieldset>
<button>Count</button>
<p>Total = <span id="result">
CertainPerformance
  • 356,069
  • 52
  • 309
  • 320
0

document.getElementsByName() returns a collection of elements. so calling value property will not work there as it does not have such property.

You can hold input elements with amount_inputs variable and iterate over it (in the example below by using spread syntax and Array.reduce())

And with Array.reduce() you can calculate the sum of the prices. There is no need for var amount = [] and var total_ary = [] variables.

Hope this helps

function Totalamount() {
  var input_cb = document.getElementsByName('cb');
  var amount_inputs = document.getElementsByName("amount")
  var total = 0;
  var price = [10, 20, 30];
  
  
  total = [...input_cb].reduce((total, cb, i) => {
    if(cb.checked){
      total += (parseInt(amount_inputs[i].value) || 0) * price[i]
      //                                     ^^^^^^^^^ This is to avoid NaN multiplication
    }
    return total
  },0);
  
  
  document.getElementById("result").innerHTML = "$" + 0;
  document.getElementById("result").innerHTML = total + "元";
}
<fieldset>
  <input type="checkbox" name="cb" checked>$10:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$20:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$30:<input type="text"  name="amount"><br>
</fieldset>
<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
Harun Yilmaz
  • 8,281
  • 3
  • 24
  • 35
0
  1. Use Index while retrieving the element from document.getElementsByName("amount");
  2. Use for loop on amount array not on total_ary

function Totalamount() {
  var input_cb = document.getElementsByName('cb');
  var amount = [];
  var total_ary = [];
  var total = 0;
  var price = [10, 20, 30];
  var i = 0;
  for (i = 0; i < input_cb.length; i++) {
    if (input_cb[i].checked) {
      amount.push(document.getElementsByName("amount")[i].value); //get amounts of the products
    } else {
      amount.push(0); //If there is no input, add 0 to the array
    }
  }
  for (i = 0; i < amount.length; i++) {
    total_ary.push(parseInt(amount[i] * price[i])); // Add the products' total price to array
    total += isNaN(parseInt(total_ary[i])) ? 0 : parseInt(total_ary[i]); //Counting the total money
  }
  document.getElementById("result").innerHTML = "$" + 0;
  document.getElementById("result").innerHTML = "$" + total ;
}
<fieldset>
  <input type="checkbox" name="cb" checked>$10:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$20:<input type="text"  name="amount"><br>
  <input type="checkbox" name="cb" checked>$30:<input type="text"  name="amount"><br>
</fieldset>
<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
Vivek Jain
  • 44
  • 6
0

You have made a few mistakes:

(1) If you want to keep all the checkboxes checked at initial stage use checked="true" in place of checked

(2) getElementsByName("amount") returns an array, so you should use the index as well

(3) total_ary length is 0 initially.. therefore, you should run the loop with input_cb. (Here, you can do both the task with a single loop: refer code below)

Refer the code with corrections:

<!DOCTYPE html>
<html>
<head>Order sys
<script>
function Totalamount() {
    var input_cb = document.getElementsByName('cb');
    var amount = [];
    var total = 0;
    var price = [10,20,30];
    var i=0;
    for (i = 0; i < input_cb.length; i++) {
        if (input_cb[i].checked){
            amount.push(parseInt(document.getElementsByName("amount")[i].value)); //get amounts of the products
        }
        else{
            amount.push(0); //If there is no input, add 0 to the array
        }

        total += parseInt(amount[i] * price[i]) //Counting the total money
    }

    document.getElementById("result").innerHTML = "$" + 0;
    document.getElementById("result").innerHTML = total + "元";
}
</script>
</head>
<body>
<fieldset>
<input type = "checkbox" name="cb" checked="true">$10:<input type="text" id="amount_milk" name="amount" ><br>
<input type = "checkbox" name="cb" checked="true">$20:<input type="text" id="amount_soymlik" name="amount"><br>
<input type = "checkbox" name="cb" checked="true">$30:<input type="text" id="amount_blacktea" name="amount" ><br>
</fieldset>
<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
</body>
</html>
Keval Bhogayata
  • 4,422
  • 3
  • 13
  • 36
0

You can refactor your code:

  • Fist use inputs of type number <input type="number" name="amount"> to accept only numbers from your end users
  • Then, you can work with indexed arrays like [...document.querySelectorAll('input[name="cb"]')] and loop only one time with Array.prototype.reduce() to get the total

Code example:

function Totalamount() {
  const inputNumberArr = [...document.querySelectorAll('input[name="cb"]')]
  const inputAmountArr = [...document.querySelectorAll('input[name="amount"]')]
  const priceArr = [10, 20, 30]
  const total = inputNumberArr.reduce((a, c, i) => {
    const num = c.checked ? +inputAmountArr[i].value : 0
    return a + num * priceArr[i]
  }, 0)
  
  document.getElementById('result').innerHTML = '$' + 0
  document.getElementById('result').innerHTML = '$' + total
}
<fieldset>
  <input type="checkbox" name="cb" checked> $10:
  <input type="number" name="amount"><br>
  <input type="checkbox" name="cb" checked> $20:
  <input type="number" name="amount"><br>
  <input type="checkbox" name="cb" checked> $30:
  <input type="number" name="amount"><br>
</fieldset>

<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
Yosvel Quintero
  • 18,669
  • 5
  • 37
  • 46
-1

Is this what you are looking for? Errors that I identified.

  1. Making use of document.getElementsByName("amount").value instead of making the respective amount field you were making use of the global selector.

  2. Trying to loop total_ary array instead of amount array.

function Totalamount() {
    var input_cb = document.getElementsByName('cb');
    var amountInput = document.getElementsByName('amount');
    var amount = [];
    var total_ary = [];
    var total = 0;
    var price = [10,20,30];
    var i=0;
    for (i = 0; i < input_cb.length; i++) {
        if (input_cb[i].checked && amountInput[i].value){
            amount.push(parseInt(amountInput[i].value)); //get amounts of the products
        }
        else{
            amount.push(0); //If there is no input, add 0 to the array
        }
    }
    for (i = 0; i < amount.length; i++) {
        total_ary.push(parseInt(amount[i] * price[i])); // Add the products' total price to array
        total += parseInt(total_ary[i]); //Counting the total money
    }
    document.getElementById("result").innerHTML = "$" + 0;
    document.getElementById("result").innerHTML = total + "元";
}
<fieldset>
  <input type = "checkbox" name="cb" checked>$10
  <input type="text" id="amount_milk" name="amount" ><br>

  <input type = "checkbox" name="cb" checked>$20
  <input type="text" id="amount_soymlik" name="amount"><br>

  <input type = "checkbox" name="cb" checked>$30
  <input type="text" id="amount_blacktea" name="amount" ><br>
</fieldset>
<button onclick="Totalamount()">Count</button>
<p>Total = <span id="result">
Nitheesh
  • 19,238
  • 3
  • 22
  • 49