Reputation: 3093
I have HTML markup like this:
<div class="FullBox">
<div class="totalPrice"></div>
<div class="item">
<div class="title">Item 1</div>
<div class="price">$35</div>
</div>
<div class="item">
<div class="title">Item 2</div>
<div class="price">$58.99</div>
</div>
</div>
<div class="FullBox">
<div class="totalPrice"></div>
<div class="item">
<div class="title">Item 3</div>
<div class="price">$22</div>
</div>
<div class="item">
<div class="title">Item 4</div>
<div class="price">$32</div>
</div>
</div>
I want to output the total price of each FullBox
in the totalPrice
class.
The final HTML should look like this:
<div class="FullBox">
<div class="totalPrice">$93.99</div>
<div class="item">
<div class="title">Item 1</div>
<div class="price">$35</div>
</div>
<div class="item">
<div class="title">Item 2</div>
<div class="price">$58.99</div>
</div>
</div>
<div class="FullBox">
<div class="totalPrice">$54</div>
<div class="item">
<div class="title">Item 3</div>
<div class="price">$22</div>
</div>
<div class="item">
<div class="title">Item 4</div>
<div class="price">$32</div>
</div>
</div>
I tried this to start:
$('.FullBox').each(function() {
$('.item').each(function() {
console.log($(this).find('.price').html();
});
});
But that gets the price of every .price
element on the page, i'm not sure how to group it and then assign it to the specific div that I want.
Upvotes: 0
Views: 45
Reputation: 56744
This is a plain vanilla Javascript solution that instead of just changing the content of totalPrice
divs also creates them.
const boxes = document.querySelectorAll('.FullBox');
for (const box of boxes) {
const totalPrice = [...box.querySelectorAll('.price')]
.map(x => Number(x.textContent.substr(1)))
.reduce((acc, val) => acc += val);
const div = document.createElement('div');
div.className = 'totalPrice';
div.textContent = `Total: $${totalPrice.toFixed(2)}`;
box.insertBefore(div, box.firstElementChild);
}
<div class="FullBox">
<div class="item">
<div class="title">Item 1</div>
<div class="price">$35</div>
</div>
<div class="item">
<div class="title">Item 2</div>
<div class="price">$58.99</div>
</div>
</div>
<hr />
<div class="FullBox">
<div class="item">
<div class="title">Item 3</div>
<div class="price">$22</div>
</div>
<div class="item">
<div class="title">Item 4</div>
<div class="price">$32</div>
</div>
</div>
Upvotes: 1
Reputation: 11055
instead of printing each price individually, add them to a counter. Also you need to limit the .item selector to the scope of its parent FullBox, so I use $(this).find("item")
instead of $(".item")
var counter;
$('.FullBox').each(function() {
counter=0;
$(this).find('.item').each(function() {
//console.log($(this).find('.price').html();
counter=counter + parseFloat($(this).find('.price').html());
});
// In the following line (this) refers to the exact parent FullBox:
$(this).prepend('<div class="totalPrice">$' + counter +'</div>');
});
Edit: As you have $ sign before numbers you need to convert them to pure digits before calculations.
counter=counter + parseFloat($(this).find('.price').html().replace('$',''))
Upvotes: 1
Reputation: 24965
// find all the total price to set the html of
$('.totalPrice').html(function(){
// get the closest fullbox for the total, and find all the prices
var $prices = $(this).closest('.FullBox').find('.item .price');
var total = $prices
// get all the prices without the dollar sign
.map((_, price) => price.innerHTML.replace('$', ''))
// get a basic array
.get()
// sum the prices, converted to float
.reduce((sum, price) => sum + parseFloat(price), 0);
// return the total, removing any precision errors
return '$'+ ( Math.floor( total * 100 ) / 100 );
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="FullBox">
<div class="totalPrice"></div>
<div class="item">
<div class="title">Item 1</div>
<div class="price">$35</div>
</div>
<div class="item">
<div class="title">Item 2</div>
<div class="price">$58.99</div>
</div>
</div>
<div class="FullBox">
<div class="totalPrice"></div>
<div class="item">
<div class="title">Item 3</div>
<div class="price">$22</div>
</div>
<div class="item">
<div class="title">Item 4</div>
<div class="price">$32</div>
</div>
</div>
Upvotes: 2