Home > other >  How to get order total if quantity is updated
How to get order total if quantity is updated

Time:04-06

Order entry form contains product name, price and quantity columns:

 <table id="order-products" >
        <colgroup>
            <col style="width: 80%;">
            <col style="width: 10%;">
            <col style="width: 10%;">
        </colgroup>

        <tbody>
                <tr>
                    <td>
                       Product1
                    </td>
                    <td>
 <span >0,98</span>
                    </td>
                    <td>
                        <input data-product="4750211645618"  id="product_Soodkogus" name="product.Soodkogus"
                       type="number" min="0" max="999999" value=""
                       onblur="orderSumRefresh()" />
                    </td>
                </tr>
        </tbody>
    </table>
    Order total <p id="js-doksumma"></p>

If quantity is changed, order total value should updated. I tried

<script>
    function parseFloatFormatted(txt) {
    if (typeof txt !== 'string' || txt === null || txt === "") {
      return 0
      }
    return parseFloat(txt.replace(',', '.').replace(' ', ''))
    }

    function orderSumRefresh() {
    let totalAmount = 0
    const table = document.getElementById("order-products")
    for (let i in table.rows) {
       const row = table.rows[i]
       const hind = row.cells[1].childNodes[0].innerHTML
       const kogus = row.cells[2].childNodes[0].innerText
       const rowSum = Math.round(parseFloatFormatted(hind)* parseFloatFormatted(kogus)  * 100) / 100
       totalAmount  = rowSum
       }
    const dok = document.getElementById("js-doksumma")
    dok.innerText = totalAmount.toFixed(2)
    }
</script>

but got error

Order?Customer=296:12733 Uncaught TypeError: Cannot read properties of undefined (reading '1')

at line

const hind = row.cells[1].childNodes[0].innerHTML

How to properly implement this ? Should pure CSS, javascript or query used?

Modern Chrome browser is used in mobile phone, ASP.NET 6 MVC Razor application.

CodePudding user response:

Your problem is from here

for (let i in table.rows) {}

The value will be "0" and "length" (not index like your expectation), so it throws an error while trying to access row.cells["length"].childNodes (row.cells["length"] is undefined)

I'd suggest you modify it to

for (const row of table.rows) {}

The full code can be

function parseFloatFormatted(txt) {
  if (typeof txt !== 'string' || txt === null || txt === "") {
    return 0
  }
  return parseFloat(txt.replace(',', '.').replace(' ', ''))
}

function orderSumRefresh() {
  let totalAmount = 0
  const table = document.getElementById("order-products")
  for (const row of table.rows) {
    const hind = row.cells[1].childNodes[0].innerHTML
    const kogus = row.cells[2].childNodes[0].innerText
    const rowSum = Math.round(parseFloatFormatted(hind) * parseFloatFormatted(kogus) * 100) / 100
    totalAmount  = rowSum
  }
  const dok = document.getElementById("js-doksumma")
  dok.innerText = totalAmount.toFixed(2)
}
<table id="order-products" >
  <colgroup>
    <col style="width: 80%;">
    <col style="width: 10%;">
    <col style="width: 10%;">
  </colgroup>

  <tbody>
    <tr>
      <td>
        Product1
      </td>
      <td>
        <span >0,98</span>
      </td>
      <td>
        <input data-product="4750211645618"  id="product_Soodkogus" name="product.Soodkogus" type="number" min="0" max="999999" value="" onblur="orderSumRefresh()" />
      </td>
    </tr>
  </tbody>
</table>
Order total
<p id="js-doksumma"></p>

CodePudding user response:

As Nick Vu said a first problem is in the for loop and I changed to:

for (let i = 0; i < table.rows.length; i  ) {

I find more problems in the code for example the index of the childNodes is wrong, using

console.log(row.cells[1].childNodes)

you can see there are 3 child and you are searching for the middle one (index: 1)

Then for accessing the data of the input element you need to use the .value property like this:

const kogus = row.cells[2].childNodes[1].value

So I think the final code is:

function parseFloatFormatted(txt) {
    if (typeof txt !== 'string' || txt === null || txt === "") {
        return 0
    }
    return parseFloat(txt.replace(',', '.').replace(' ', ''))
}

function orderSumRefresh() {
    let totalAmount = 0
    const table = document.getElementById("order-products")
    for (let i = 0; i < table.rows.length; i  ) {
        const row = table.rows[i]
        const hind = row.cells[1].childNodes[1].innerHTML
        const kogus = row.cells[2].childNodes[1].value
        const rowSum = Math.round(parseFloatFormatted(hind) * parseFloatFormatted(kogus) * 100) / 100
        totalAmount  = rowSum
    }
    const dok = document.getElementById("js-doksumma")
    dok.innerText = totalAmount.toFixed(2)
}
<table id="order-products" >
    <colgroup>
        <col style="width: 80%;">
        <col style="width: 10%;">
        <col style="width: 10%;">
    </colgroup>

    <tbody>
        <tr>
            <td>
                Product1
            </td>
            <td>
                <span >0,98</span>
            </td>
            <td>
                <input data-product="4750211645618"  id="product_Soodkogus" name="product.Soodkogus"
                    type="number" min="0" max="999999" value="" onblur="orderSumRefresh()" />
            </td>
        </tr>
    </tbody>
</table>
Order total <p id="js-doksumma"></p>

I suggest you to use the console.log() and log some variable to see if there is somethink wrong with the code.

  • Related