基于jQuery的表格CRUD与本地存储添加行失效问题排查
解决jQuery CRUD表格「Add New」按钮仅能首次添加的问题
问题原因
- 静态DOM元素重复使用:原代码中
myEmptyRow的输入框和按钮是提前创建好的jQuery对象,第一次添加到DOM后,这些元素已属于页面节点,无法被重复插入到新行,导致后续点击添加时无元素可渲染。 - 函数参数传递错误:
addRow函数定义为(target, data, empty),但按钮点击时传入了4个参数,导致empty被错误赋值为myButtons对象,触发不必要的tbody清空逻辑。 - 行数据长度判断偏差:
addRow中if (data.length ==4)的判断对应已保存的4列数据(不含操作列),但新添加的空行是5列数据(含操作列),该判断不会执行,但空行本身已包含操作按钮,无需额外处理。
修复步骤
- 将
myEmptyRow从静态数组改为函数,每次调用时动态生成新的输入框和按钮元素,确保每次添加的新行都是全新的DOM节点。 - 修正
btnAdd点击事件中addRow的调用参数,去掉多余的myButtons,正确传递empty布尔值。
修改后的完整代码
<!DOCTYPE html> <html lang="en"> <head> <title>CRUD Table jQuery</title> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1"> <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/4.5.2/css/bootstrap.min.css"> <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script> </head> <body> <div class="container"> <div class="row"> <div class="col-md-12 text-right"> <input type="button" id="btnAdd" class="btn btn-primary para" value="Add New" /> </div> </div> <div class="row pt-3"> <div class="col-md-12 col-sm-12 col-12 p-2 "> <table id="tblData" class="table table-bordered table-hover table-striped"> <thead> <tr id="headings"> <th class="schedule-color heading">ID</th> <th class="schedule-color heading">Name</th> <th class="schedule-color heading">Address</th> <th class="schedule-color heading">Age</th> <th class="tdaction">Action</th> </tr> </thead> <tbody class="searchable"> </tbody> </table> </div> </div> </div> <script> $(function() { // 改为函数,每次调用生成新的空行元素 function getMyEmptyRow() { return [{ class: "tdID", content: $("<input>", { type: "text", class: "form-control txtID" }) }, { class: "tdName", content: $("<input>", { type: "text", class: "form-control txtName"}) }, { class: "tdAddress", content: $("<input>", { type: "text", class: "form-control txtAddress"}) }, { class: "tdAge", content: $("<input>", { type: "text", class: "form-control txtAge" }) }, { class: "tdAction", content: [ $("<button>", { class: "btn btn-sm btn-success btn-save" }).html("Save"), $("<button>", { class: "btn btn-sm btn-success btn-cancel" }).html("Delete") ] }]; } var myButtons = { edit: [ $("<button>", { class: "btn btn-success btn-sm btn-edit" }).html("Edit"), $("<button>", { class: "btn btn-danger btn-sm" }).html("Delete") ], update: [ $("<button>", { class: "btn btn-success btn-sm btn-save" }).html("Update"), $("<button>", { class: "btn btn-danger btn-sm" }).html("Delete") ] }; function getStore(index) { console.log("Get data for " + index); return JSON.parse(localStorage.getItem(index)); } function saveStore(index, data) { console.log("Saving Data to " + index, data); localStorage.setItem(index, JSON.stringify(data)); } function deleteStore(index) { console.log("Deleting Data for " + index); localStorage.removeItem(index); } function addRow(target, data, empty) { if (target == undefined) { target = $("table:eq(0)"); } if (empty == undefined) { empty = false; } if (data == null) { return false; } console.log("Add Row to " + target.attr("id"), empty); if (empty) { $("tbody", target).html(""); } var row = $("<tr>").appendTo($("tbody", target)); if (data == undefined) { $("<td>", { colspan: 4, class: "text-center" }).appendTo(row); } else { row.addClass("trNewRow"); $.each(data, function(i, cell) { $("<td>", { class: cell.class }).append(cell.content).appendTo(row); }); } if (data.length == 4) { $("<td>", { class: "tdAction" }).append(myButtons.edit).appendTo(row); } return row; } function saveRow(row) { if (row == undefined) { return false; } var rowData = [{ class: "tdID", content: $(".txtID", row).val() },{ class: "tdName", content: $(".txtName", row).val() }, { class: "tdAddress", content: $(".txtAddress", row).val() }, { class: "tdAge", content: $(".txtAge", row).val() } ]; $.each(rowData, function(i, c) { $("." + c.class, row).html(c.content); }); $(".tdAction", row).html(myButtons.edit); saveStore("row-" + row.index(), rowData); } function init() { if (localStorage.length == 0) { addRow($("#tblData")); } else { console.log("Found Local Storage. Rows: " + localStorage.length); $.each(localStorage, function(k, o) { var rowData = getStore(k); console.log(k, rowData); addRow($("#tblData"), rowData); }); } } init(); $("#btnAdd").click(function() { // 调用函数获取新的空行数据,修正参数传递 addRow($("#tblData"), getMyEmptyRow(), $("#tblData tbody tr td").length == 1 ? true : false); }); $('#tblData').on('click', '.btn-save', function() { saveRow($(this).closest("tr")); }); $('#tblData').on('click', '.btn-danger, .btn-cancel', function() { deleteStore("row-" + $(this).closest("tr").index()); $(this).closest("tr").remove(); if ($("#tblData tbody tr").length == 0) { addRow($("#tblData ")); } }); $('#tblData').on('click', '.btn-edit', function() { var row = $(this).closest("tr"); $(".tdID", row).html("<input type='text' value='" + $(".tdID", row).html() + "' class='form-control txtID' />"); $(".tdName", row).html("<input type='text' value='" + $(".tdName", row).html() + "' class='form-control txtName' />"); $(".tdAddress", row).html("<input type='text' value='" + $(".tdAddress", row).html() + "' class='form-control txtAddress' />"); $(".tdAge", row).html("<input type='text' value='" + $(".tdAge", row).html() + "' class='form-control txtAge' />"); $(".tdAction", row).html(myButtons.update); }); }); </script> </body> </html>
内容的提问来源于stack exchange,提问作者Nirantharika Selvachandran
相关产品推荐
相关产品推荐

