简体   繁体   English

JQuery总结具有唯一id元素的行

[英]JQuery sum rows with unique id elements

I'm looking for a way to display the sum of all the input elements (quantity and amount) respectively in the last 2 cells of each line.我正在寻找一种方法来分别在每行的最后 2 个单元格中显示所有输入元素(数量和数量)的总和。 Every element in this table has a unique id.该表中的每个元素都有一个唯一的 id。 Each input element has an id that contains information about the row it appears in :每个输入元素都有一个 id,其中包含有关它出现在的行的信息:

 var trRows = ['tr2', 'tr3', 'tr4', 'tr5', 'tr6', 'tr7', 'tr8', 'tr9', 'tr10', 'tr11', 'tr12']; trRows.forEach(function(trRow) { var $sumQuantity = 0; var $sumAmount = 0; $(this).find('#tr' + trRow + 'input[id *= "qty"]').each(function() { $sumQuantity += +$(this).text() || 0; }); $(this).find('#tr' + trRow + 'input[id *= "amount"]').each(function() { $sumAmount += +$(this).text() || 0; }); $('#sumQtyTR' + trRows, this).html($sumQuantity); $('#sumAmountTR' + trRows, this).html($sumAmount); });
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <table> <tr id='tr2'> <td id='td2_65'><span id='span_i2qty_65'><input id='input_i2qty_65' class='editbox'></span> </td> <td id='td2_65'><span id='span_i2amount_65'><input id='input_i2amount_65' class='editbox'></span> </td> <td id='td2_66'><span id='span_i2qty_66'><input id='input_i2qty_66' class='editbox'></span> </td> <td id='td2_66'><span id='span_i2amount_66'><input id='input_i2amount_66' class='editbox'></span> </td> <td id='sumQtyTR2'></td> <td id='sumAmountTR2'></td> </tr> <tr id='tr3'> <td id='td3_65'><span id='span_i3qty_65'><input id='input_i3qty_65' class='editbox'></span> </td> <td id='td3_65'><span id='span_i3amount_65'><input id='input_i3amount_65' class='editbox'></span> </td> <td id='td3_66'><span id='span_i3qty_66'><input id='input_i3qty_66' class='editbox'></span> </td> <td id='td3_66'><span id='span_i3amount_66'><input id='input_i3amount_66' class='editbox'></span> </td> <td id='sumQtyTR3'></td> <td id='sumAmountTR3'></td> </tr> <!-- More rows --> </table>

I can't figure out why sums are not displayed.我不明白为什么不显示总和。 Selectors ?选择器? Thanks谢谢

Recommendations建议

Within your code there are a few points of interest that may be worth consideration to reduce the clutter:在您的代码中,有一些兴趣点可能值得考虑以减少混乱:

  1. IDs are intended to be unique. ID 旨在是唯一的。 There should never be a time where an ID is used in more than one place in an HTML document.永远不应该出现在 HTML 文档中不止一个地方使用 ID 的情况。 In places where you think two or more elements might share an id , you should use a class instead在您认为两个或多个元素可能共享一个id ,您应该改用class
  2. Unless you are using jQuery elsewhere, you should know that jQuery is not necessary.除非您在其他地方使用 jQuery,否则您应该知道 jQuery 不是必需的。 It does provide several advantages (including cross-browser compliance), but you should consider using native JavaScript and a packager that will add the necessary polyfills它确实提供了几个优点(包括跨浏览器合规性),但您应该考虑使用原生 JavaScript 和一个打包器来添加必要的 polyfills

Examples例子

The examples below are intended to be close in structure/design to the original source code in the OP for learning purposes;以下示例旨在在结构/设计上接近 OP 中的原始源代码,以供学习之用; however, it should be noted that there are many ways to optimize to improve performance and readability.但是需要注意的是,优化的方式有很多,可以提高性能和可读性。

One major point worth mentioning is in the logic flow.值得一提的一个要点是逻辑流程。 The structure in these examples are inefficient, since every time an input is updated it is looping over and recalculating sums for all of the rows.这些示例中的结构效率低下,因为每次更新输入时,它都会循环并重新计算所有行的总和。 This could be improved by only calculating and updating the sum of the altered row.这可以通过仅计算和更新更改行的总和来改进。 Additionally, holding an array of interested rows (eg, row_ids ) could be better improved with more semantic HTML and the use of classes (if needing to be selective).此外,通过更多语义 HTML 和类的使用(如果需要有选择性),可以更好地保存感兴趣的行数组(例如row_ids )。

There are some other major changes made to both the jQuery and ES6+ example below.下面的 jQuery 和 ES6+ 示例还进行了一些其他重大更改。 Most notably is the onChange event handler.最值得注意的是 onChange 事件处理程序。 The code in the OP iterated over each ID immediately on page load, but never again. OP 中的代码在页面加载时立即迭代每个 ID,但不再重复。 There needed to be a hook into some event that would be called when the input box was modified;需要有一个钩子到某个事件中,当输入框被修改时会被调用; thus the onChange or onBlur event is necessary in order to re-calculate the values.因此 onChange 或 onBlur 事件是必要的,以便重新计算值。

jQuery Example jQuery 示例

Given these two recommendations, I've made some substantial changes to your HTML and JavaScript, which include but are not limited to:鉴于这两个建议,我对您的 HTML 和 JavaScript 进行了一些重大更改,其中包括但不限于:

  • removed unnecessary IDs and added respective classes删除了不必要的 ID 并添加了相应的类
  • use reduce for sum calculation使用 reduce 进行总和计算

 jQuery(document).ready(function($) { let row_ids = ['tr2', 'tr3', 'tr4', 'tr5', 'tr6', 'tr7', 'tr8', 'tr9', 'tr10', 'tr11', 'tr12']; function changeEventHandler() { $.each(row_ids, function(ndx, row_id) { const $row = $('#' + row_id) if (!$row.length) return; const quantity = $row.find('input.quantity').get().reduce(function(acc, input) { acc += parseFloat(input.value) || 0; return acc }, 0) const amount = $row.find('input.amount').get().reduce(function(acc, input) { acc += parseFloat(input.value) || 0; return acc }, 0) $row.find('.sum.quantity').text(quantity) $row.find('.sum.amount').text(amount) }); } $(document).on('change', 'input', changeEventHandler) })
 .sum { background: #eee; } th,td { vertical-align: bottom; white-space: nowrap; text-align: center; } table { width: 100%; } input { width: 40%; }
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> Fill in each input with a number (watch sums auto-update): <table> <thead> <tr> <th>QTY 1</th> <th>AMT 1</th> <th>QTY 2</th> <th>AMT 2</th> <th>SUM QTY</th> <th>SUM AMT</th> </tr> </thead> <tbody> <tr id='tr2'> <!-- td: use class and not id --> <!-- remove unnecessary classes --> <td class="item_65"><span><input class='quantity'></span></td> <td class="item_65"><span><input class='amount'></span></td> <td class="item_66"><span><input class='quantity'></span></td> <td class="item_66"><span><input class='amount'></span></td> <td class="sum quantity"></td> <td class="sum amount"></td> </tr> <tr id='tr3'> <td class="item_65"><span><input class='quantity'></span></td> <td class="item_65"><span><input class='amount'></span></td> <td class="item_66"><span><input class='quantity'></span></td> <td class="item_66"><span><input class='amount'></span></td> <td class="sum quantity"></td> <td class="sum amount"></td> </tr> <!-- More rows --> </tbody> </table>


ES6+ Example ES6+ 示例

Given the two recommendations, I've made some substantial changes to your HTML and JavaScript, which include but are not limited to:鉴于这两个建议,我对您的 HTML 和 JavaScript 进行了一些重大更改,其中包括但不限于:

  • removed unnecessary IDs and added respective classes删除了不必要的 ID 并添加了相应的类
  • removed unnecessary jQuery code (used native event handling)删除了不必要的 jQuery 代码(使用本机事件处理)
  • use reduce for sum calculation使用reduce进行总和计算
  • use arrow functions for simplified syntax使用箭头函数来简化语法

Note: as mentioned prior, the code may not work in all browsers (all versions and variations), but should work in most of the newer browsers.注意:如前所述,该代码可能不适用于所有浏览器(所有版本和变体),但应该适用于大多数较新的浏览器。 The snippet will work in most (if not all) because it is configured to use babel该代码段将在大多数(如果不是全部)中工作,因为它被配置为使用 babel

 function changeEventHandler() { let row_ids = ['tr2', 'tr3', 'tr4', 'tr5', 'tr6', 'tr7', 'tr8', 'tr9', 'tr10', 'tr11', 'tr12']; // could iterate over the rows: // document.querySelectorAll(selector) // where selector is 'tr' or '[id^="tr"]' row_ids.forEach(row_id => { const row = document.querySelector(`#${row_id}`) if (row == null) return; const qty_el = row.querySelectorAll('input.quantity') const quantity = [...qty_el].reduce((acc, cv) => acc += parseFloat(cv.value) || 0, 0) const amt_el = row.querySelectorAll('input.amount') const amount = [...amt_el].reduce((acc, cv) => acc += parseFloat(cv.value) || 0, 0) row.querySelector('.sum.quantity').textContent = quantity row.querySelector('.sum.amount').textContent = amount }); } window.setTimeout(function() { document.querySelectorAll('input').forEach(() => this.onchange = changeEventHandler) },0);
 .sum { background: #eee; } th,td { vertical-align: bottom; white-space: nowrap; text-align: center; } table { width: 100%; } input { width: 40%; }
 Fill in each input with a number (watch sums auto-update): <table> <thead> <tr> <th>QTY 1</th> <th>AMT 1</th> <th>QTY 2</th> <th>AMT 2</th> <th>SUM QTY</th> <th>SUM AMT</th> </tr> </thead> <tbody> <tr id='tr2'> <!-- td: use class and not id --> <!-- remove unnecessary classes --> <td class="item_65"><span><input class='quantity'></span></td> <td class="item_65"><span><input class='amount'></span></td> <td class="item_66"><span><input class='quantity'></span></td> <td class="item_66"><span><input class='amount'></span></td> <td class="sum quantity"></td> <td class="sum amount"></td> </tr> <tr id='tr3'> <td class="item_65"><span><input class='quantity'></span></td> <td class="item_65"><span><input class='amount'></span></td> <td class="item_66"><span><input class='quantity'></span></td> <td class="item_66"><span><input class='amount'></span></td> <td class="sum quantity"></td> <td class="sum amount"></td> </tr> <!-- More rows --> </tbody> </table>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM