Background: I am creating a simple html order form for around 30 items using pure vanilla JavaScript (no jQuery) and basic CSS. It will not involve any online payments. New items may be added by my client and they will simply copy paste a block of code for an existing item in the html of the article and give it a new item name. They will not have access to the JavaScript. To avoid potential unwanted duplicates I am using only CSS classes and no element IDs. The form consists of a item name (text), a price and two input fields - one for quantity and one for total, with total being based dynamically on price*quantity as the form is filled.
My query: The quantity and form fields are pre-filled with zeros using a forEach loop and that works fine for all elements as expected. What I cannot get to work is a second loop which calculates the total price based on price x quantity for anything other than the first one it finds.
What am I missing? Is it something to do with the onblur="calculate" command in the quantity input element? I have to admit I found this part in someone else's code and haven't used it before. Perhaps I should be using something else.
I have looked at other questions in a similar vein on here (and elsewhere) but they're either using jQuery or other types of JS or tables and so on.
The code is below. TIA:
if (document.querySelector('.order-form')) {
let qty = document.querySelectorAll('.qty');
let total = document.querySelectorAll('.total');
[].forEach.call(qty, function(zero) {
zero.setAttribute('value','0');
});
[].forEach.call(total, function(zero) {
zero.setAttribute('value','0');
})
}
calculate = function() {
let qty = document.querySelectorAll('.qty');
[].forEach.call(qty, function() {
let price = document.querySelector('.price').innerText;
let newprice = parseFloat(price).toFixed(2);
let qty = document.querySelector('.qty').value;
let newtotal = parseFloat((newprice)*(qty)).toFixed(2);
let total = document.querySelector('.total');
total.setAttribute('value',newtotal);
});
}
.order-form {
margin: 16px;
width: 100%;
}
.row {
width: 100%;
}
.prod {
margin-top: 16px;
}
.price {
width: 10%;
display: inline-block;
}
.price:before {
content: "Price: £";
}
.input-style {
width: 70%;
display: inline-block;
}
label {
padding: 0 16px;
}
<div class="order-form">
<div class="prod">Subscription Receipt Book</div>
<div class="row">
<div class="price" style="width: 10%; display: inline-block;">4.50</div>
<div class="input-style">
<label for="qty">Qty:</label><input class="qty" type="text" name="qty" onblur="calculate()" />
<label for="total_amt">Total: £</label><input class="total" type="text" name="total_amt" /></div>
</div>
<div class="row" style="width: 100%;">
<div class="prod">General Receipt Book</div>
<div class="price" style="width: 10%; display: inline-block;">4.00</div>
<div class="input-style">
<label for="qty">Qty:</label><input class="qty" type="text" name="qty" onblur="calculate()" />
<label for="total_amt">Total: £</label><input class="total" type="text" name="total_amt" />
</div>
</div>
<div class="row" style="width: 100%;">
<div class="prod">Minutes book</div>
<div class="price" style="width: 10%; display: inline-block;">5.50</div>
<div class="input-style">
<label for="qty">Qty:</label><input class="qty" type="text" name="qty" onblur="calculate()" />
<label for="total_amt">Total: £</label><input class="total" type="text" name="total_amt" />
</div>
</div>
</div>