Skip to content
Advertisement

How to sort div, depending on the values that are contained in their children?

I am outputting data from a file using .map(), so to get all the values the parent I use .forEach() (Otherwise, only one div with class="price" will be selected, instead of 20). I need to sort all div that contain child with the amount from smallest to largest.

I am getting the child like this:

document.querySelectorAll('.price').forEach((v => (Number(v.textContent))));

console.log(Number(v.textContent));

12    
31   
25     // a number is printed on each line of the console
42
3
41

But I don’t know how to sort the parent div based on the value of the child.

Advertisement

Answer

So you can convert your NodeList from querySelectorAll to an Array then you can use array methods as normal:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Sort Nodes By textContent Example</title>
</head>
<body>
<p class="price">12</p>
<p class="price">31</p>
<p class="price">25</p>
<p class="price">42</p>
<p class="price">3</p>
<p class="price">41</p>
<script>
    const prices = [...document.querySelectorAll('.price')]
        .map(v => Number(v.textContent))
        .sort((a, b) => a - b);
    console.log(prices)
</script>
</body>
</html>

You can switch the sort function to b - a if you wanted descending order instead.


If you wanted to actually replace the DOM elements with the sorted elements you could do something like:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Sort and Replace Nodes In DIV By textContent Example</title>
</head>
<body>
<div id="container">
    <p class="price">12</p>
    <p class="price">31</p>
    <p class="price">25</p>
    <p class="price">42</p>
    <p class="price">3</p>
    <p class="price">41</p>
</div>
<script>
    const sortedPriceNodes = [...document.querySelectorAll('.price')]
        .sort((a, b) => Number(a.textContent) - Number(b.textContent));
    document.getElementById("container").replaceWith(...sortedPriceNodes);
</script>
</body>
</html>

Assuming your .price elements are not so neatly arranged:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Sort and Replace Nodes Anywhere By textContent Example</title>
</head>
<body>
<div style="background-color:lightblue">
    <p class="price">12</p>
    <div style="background-color:lightcoral">
        <p class="price">31</p>
    </div>
    <p class="price">25</p></div>
<p class="price">42</p>
<div style="background-color:lightgrey">
    <p class="price">3</p>
</div>
<p class="price">41</p>
<script>
    const priceNodes = document.querySelectorAll('.price');
    const sortedPriceNodes = [...priceNodes]
        .sort((a, b) => Number(a.textContent) - Number(b.textContent));
    priceNodes.forEach((node, index) => {
        node.replaceWith(sortedPriceNodes[index].cloneNode(true));
    })
</script>
</body>
</html>
User contributions licensed under: CC BY-SA
4 People found this is helpful
Advertisement