Làm thế nào để làm cho ô bảng HTML có thể chỉnh sửa được?


102

Tôi muốn làm cho một số ô của bảng html có thể chỉnh sửa, chỉ cần nhấp đúp vào ô, nhập một số văn bản và các thay đổi có thể được gửi đến máy chủ. Tôi không muốn sử dụng một số bộ công cụ như lưới dữ liệu dojo. Bởi vì nó cung cấp một số tính năng khác. Bạn có thể cung cấp cho tôi một số đoạn mã hoặc lời khuyên về cách triển khai nó không?

Câu trả lời:


116

Bạn có thể sử dụng thuộc tính contenteditable trên các ô, hàng hoặc bảng được đề cập.

Đã cập nhật để tương thích với IE8

<table>
<tr><td><div contenteditable>I'm editable</div></td><td><div contenteditable>I'm also editable</div></td></tr>
<tr><td>I'm not editable</td></tr>
</table>

Chỉ cần lưu ý rằng nếu bạn làm cho bảng có thể chỉnh sửa được thì ít nhất trong Mozilla, bạn có thể xóa các hàng, v.v.

Bạn cũng cần kiểm tra xem trình duyệt của đối tượng mục tiêu của bạn có hỗ trợ thuộc tính này hay không.

Khi lắng nghe các thay đổi (để bạn có thể gửi đến máy chủ), hãy xem các sự kiện thay đổi có thể chấp nhận được


Cảm ơn bạn. Có vẻ như nội dung có thể được hỗ trợ trong HTML5. Tôi đang tìm kiếm một giải pháp hoạt động trong html4.
wqfeng

Mặc dù cuối cùng nó đã được mã hóa theo tiêu chuẩn với HTML5, nhưng nó đã được hỗ trợ tốt trong hầu hết các trình duyệt cũ hơn (ngoại trừ chỉ hỗ trợ một phần trong FF3): caniuse.com/contentitable (mặc dù không có trong thiết bị di động)
Brett Zamir

Mẹo hay. Tôi đã tìm kiếm nó. Cảm ơn bạn.
praneybehl

Cám ơn về tiền bo nhiều.
Prasad Rajapaksha

1
Nếu bạn cần khả năng tương thích với IE8, bạn chỉ cần thêm contenteditablediv bất cứ khi nào tạo mới <td>. Nếu không, như đã đề cập trong bài đăng, bạn có thể thêm contenteditablevào ô, hàng hoặc bảng.
Brett Zamir

61

HTML5 hỗ trợ có thể thay đổi nội dung,

<table border="3">
<thead>
<tr>Heading 1</tr>
<tr>Heading 2</tr>
</thead>
<tbody>
<tr>
<td contenteditable='true'></td>
<td contenteditable='true'></td>
</tr>
<tr>
<td contenteditable='true'></td>
<td contenteditable='true'></td>
</tr>
</tbody>
</table>

Bên thứ 3 chỉnh sửa

Để trích dẫn mục nhập mdn trên contenteditable

Thuộc tính phải nhận một trong các giá trị sau:

  • true hoặc chuỗi trống, chỉ ra rằng phần tử phải có thể chỉnh sửa được;

  • false, cho biết rằng phần tử không được chỉnh sửa.

Nếu thuộc tính này không được đặt, giá trị mặc định của nó sẽ được kế thừa từ phần tử mẹ của nó.

Thuộc tính này là thuộc tính được liệt kê chứ không phải thuộc tính Boolean. Điều này có nghĩa là việc sử dụng rõ ràng một trong các giá trị true, false hoặc chuỗi trống là bắt buộc và không được phép sử dụng tốc ký ...

// wrong not allowed
<label contenteditable>Example Label</label> 

// correct usage
<label contenteditable="true">Example Label</label>.

Kỳ dị. Thông thường giá trị thuộc tính không phải là giá trị true, đó là bất kể tên nào. Ví dụ <td contenteditable='contenteditable'></td>,.
chạy thận

1
Các trạng thái có thể có của contenteditable : contenteditable ** = "" hoặc ** contenteditable ** = "true" Cho biết rằng phần tử có thể chỉnh sửa được. ** contenteditable ** = "false" Chỉ ra rằng phần tử không thể chỉnh sửa được. ** contenteditable ** = "inherit" Cho biết rằng phần tử có thể chỉnh sửa được nếu phần tử mẹ trực tiếp của nó có thể chỉnh sửa được. Đây là giá trị mặc định. Khi bạn thêm ** contenteditable vào một phần tử, trình duyệt sẽ làm cho phần tử đó có thể chỉnh sửa được. Ngoài ra, mọi phần tử con của phần tử đó cũng sẽ có thể chỉnh sửa trừ khi các phần tử con đó rõ ràng là ** contenteditable ** = "false".
vardhan

1
Tôi biết điều đó, tôi chỉ nghĩ rằng nó rất kỳ lạ vì hầu hết các thuộc tính khác không có cú pháp đó.
chạy thận

17

Tôi có ba cách tiếp cận, Ở đây bạn có thể sử dụng cả hai <input>hoặc <textarea>tùy theo yêu cầu của bạn.

1. Sử dụng Nhập vào <td>.

Sử dụng <input>phần tử trong tất cả các <td>s,

<tr><td><input type="text"></td>....</tr>

Ngoài ra, bạn có thể muốn thay đổi kích thước đầu vào thành kích thước của nó td. Ví dụ.,

input { width:100%; height:100%; }

Ngoài ra, bạn có thể thay đổi màu của đường viền của hộp nhập liệu khi nó không được chỉnh sửa.

2. Sử dụng contenteditable='true'thuộc tính. (HTML5)

Tuy nhiên, nếu bạn muốn sử dụng contenteditable='true' , bạn cũng có thể muốn lưu các giá trị thích hợp vào cơ sở dữ liệu. Bạn có thể đạt được điều này với ajax.

Bạn có thể đính kèm keyhandlers keyup, keydown, keypressvv đến <td>. Ngoài ra, tốt hơn là sử dụng một số delay () với các sự kiện đó khi người dùng liên tục nhập, sự kiện ajax sẽ không kích hoạt với mỗi lần người dùng nhấn phím. ví dụ,

$('table td').keyup(function() {
  clearTimeout($.data(this, 'timer'));
  var wait = setTimeout(saveData, 500); // delay after user types
  $(this).data('timer', wait);
});
function saveData() {
  // ... ajax ...
}

3. Nối <input>vào <td>khi nó được nhấp vào.

Thêm phần tử đầu vào tdkhi <td>được nhấp vào, thay thế giá trị của nó theo tdgiá trị của. Khi đầu vào bị mờ, hãy thay đổi giá trị của `td bằng giá trị của đầu vào. Tất cả điều này với javascript.


Rất tiếc, bạn đã bỏ lỡ phần câu hỏi "Làm thế nào để có thể chỉnh sửa ô bảng HTML?" đặc biệt là trong ví dụ 2. Người dùng đã hỏi làm thế nào để đạt được điều này trên doubleclick. Bạn có thể vui lòng thực hiện phần còn thiếu?
Robert

@BhaveshGangani tôi có một số vấn đề, contenteditable=truebạn có thể giúp tôi về vấn đề này được không?

1
Chắc chắn tôi có thể thử. Bạn có một js khó khăn cho điều đó?
Bhavesh Gangani

6

Đây là một ví dụ có thể chạy được.

$(function(){
  $("td").click(function(event){
    if($(this).children("input").length > 0)
          return false;

    var tdObj = $(this);
    var preText = tdObj.html();
    var inputObj = $("<input type='text' />");
    tdObj.html("");

    inputObj.width(tdObj.width())
            .height(tdObj.height())
            .css({border:"0px",fontSize:"17px"})
            .val(preText)
            .appendTo(tdObj)
            .trigger("focus")
            .trigger("select");

    inputObj.keyup(function(event){
      if(13 == event.which) { // press ENTER-key
        var text = $(this).val();
        tdObj.html(text);
      }
      else if(27 == event.which) {  // press ESC-key
        tdObj.html(preText);
      }
    });

    inputObj.click(function(){
      return false;
    });
  });
});
<html>
    <head>
        <!-- jQuery source -->
        <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
    </head>
    <body>
        <table align="center">
            <tr> <td>id</td> <td>name</td> </tr>
            <tr> <td>001</td> <td>dog</td> </tr>
            <tr> <td>002</td> <td>cat</td> </tr>
            <tr> <td>003</td> <td>pig</td> </tr>
        </table>
    </body>
</html>



4

Hãy thử mã này.

$(function () {
 $("td").dblclick(function () {
    var OriginalContent = $(this).text();

    $(this).addClass("cellEditing");
    $(this).html("<input type="text" value="&quot; + OriginalContent + &quot;" />");
    $(this).children().first().focus();

    $(this).children().first().keypress(function (e) {
        if (e.which == 13) {
            var newContent = $(this).val();
            $(this).parent().text(newContent);
            $(this).parent().removeClass("cellEditing");
        }
    });

 $(this).children().first().blur(function(){
    $(this).parent().text(OriginalContent);
    $(this).parent().removeClass("cellEditing");
 });
 });
});

Bạn cũng có thể truy cập liên kết này để biết thêm chi tiết:


Để tránh các sự cố trong IE với $ (this) .children (). First (). Focus (); - stackoverflow.com/a/3562193/5234417
Alexei Zababurin


4

Tôi đang sử dụng cái này cho trường có thể chỉnh sửa

<table class="table table-bordered table-responsive-md table-striped text-center">
  <thead>
    <tr>
      <th class="text-center">Citation</th>
      <th class="text-center">Security</th>
      <th class="text-center">Implementation</th>
      <th class="text-center">Description</th>
      <th class="text-center">Solution</th>
      <th class="text-center">Remove</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td class="pt-3-half" contenteditable="false">Aurelia Vega</td>
      <td class="pt-3-half" contenteditable="false">30</td>
      <td class="pt-3-half" contenteditable="false">Deepends</td>
      <td class="pt-3-half" contenteditable="true"><input type="text" name="add1" value="spain" class="border-none"></td>
      <td class="pt-3-half" contenteditable="true"><input type="text" name="add1" value="marid" class="border-none"></td>
      <td>
        <span class="table-remove"><button type="button"
                              class="btn btn-danger btn-rounded btn-sm my-0">Remove</button></span>
      </td>
    </tr>
  </tbody>
</table>


3

Nếu bạn sử dụng Jquery, plugin này giúp bạn rất đơn giản, nhưng rất tốt

https://github.com/samuelsantosdev/TableEdit


2
Đó trông giống như một plugin thú vị. Tài liệu về cách sử dụng nó có thể được tìm thấy trong tệp index.html. Vui lòng xem qua meta.stackexchange.com/questions/8231/… để biết lý do tại sao bao gồm nhiều thông tin hơn chỉ là một liên kết tạo ra câu trả lời tốt hơn.
Jason Aller

3

Đây là điểm cần thiết mặc dù bạn không cần phải làm cho mã lộn xộn như thế này. Thay vào đó, bạn chỉ có thể lặp lại tất cả <td>và thêm <input>các thuộc tính và cuối cùng đặt các giá trị vào.

function edit(el) {
  el.childNodes[0].removeAttribute("disabled");
  el.childNodes[0].focus();
  window.getSelection().removeAllRanges();
}
function disable(el) {
  el.setAttribute("disabled","");
}
<table border>
<tr>
<td ondblclick="edit(this)"><input value="cell1" disabled onblur="disable(this)"></td>
<td ondblclick="edit(this)"><input value="cell2" disabled onblur="disable(this)"></td>
<td ondblclick="edit(this)"><input value="cell3" disabled onblur="disable(this)"></td>
<td ondblclick="edit(this)"><input value="so forth..." disabled onblur="disable(this)">
</td>
</tr>
</table>


0

điều này thực sự rất dễ hiểu, đây là mẫu HTML, jQuery .. của tôi và nó hoạt động như một sự quyến rũ, tôi xây dựng tất cả mã bằng cách sử dụng mẫu dữ liệu json trực tuyến. hoan hô

<< HTML >>

<table id="myTable"></table>

<< jQuery >>

<script>
        var url = 'http://jsonplaceholder.typicode.com/posts';
        var currentEditedIndex = -1;
        $(document).ready(function () {
            $.getJSON(url,
            function (json) {
                var tr;
                tr = $('<tr/>');
                tr.append("<td>ID</td>");
                tr.append("<td>userId</td>");
                tr.append("<td>title</td>");
                tr.append("<td>body</td>");
                tr.append("<td>edit</td>");
                $('#myTable').append(tr);

                for (var i = 0; i < json.length; i++) {
                    tr = $('<tr/>');
                    tr.append("<td>" + json[i].id + "</td>");
                    tr.append("<td>" + json[i].userId + "</td>");
                    tr.append("<td>" + json[i].title + "</td>");
                    tr.append("<td>" + json[i].body + "</td>");
                    tr.append("<td><input type='button' value='edit' id='edit' onclick='myfunc(" + i + ")' /></td>");
                    $('#myTable').append(tr);
                }
            });


        });


        function myfunc(rowindex) {

            rowindex++;
            console.log(currentEditedIndex)
            if (currentEditedIndex != -1) {  //not first time to click
                cancelClick(rowindex)
            }
            else {
                cancelClick(currentEditedIndex)
            }

            currentEditedIndex = rowindex; //update the global variable to current edit location

            //get cells values
            var cell1 = ($("#myTable tr:eq(" + (rowindex) + ") td:eq(0)").text());
            var cell2 = ($("#myTable tr:eq(" + (rowindex) + ") td:eq(1)").text());
            var cell3 = ($("#myTable tr:eq(" + (rowindex) + ") td:eq(2)").text());
            var cell4 = ($("#myTable tr:eq(" + (rowindex) + ") td:eq(3)").text());

            //remove text from previous click


            //add a cancel button
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(4)").append(" <input type='button' onclick='cancelClick("+rowindex+")' id='cancelBtn' value='Cancel'  />");
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(4)").css("width", "200");

            //make it a text box
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(0)").html(" <input type='text' id='mycustomid' value='" + cell1 + "' style='width:30px' />");
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(1)").html(" <input type='text' id='mycustomuserId' value='" + cell2 + "' style='width:30px' />");
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(2)").html(" <input type='text' id='mycustomtitle' value='" + cell3 + "' style='width:130px' />");
            $("#myTable tr:eq(" + (rowindex) + ") td:eq(3)").html(" <input type='text' id='mycustomedit' value='" + cell4 + "' style='width:400px' />");

        }

        //on cancel, remove the controls and remove the cancel btn
        function cancelClick(indx)
        {

            //console.log('edit is at row>> rowindex:' + currentEditedIndex);
            indx = currentEditedIndex;

            var cell1 = ($("#myTable #mycustomid").val());
            var cell2 = ($("#myTable #mycustomuserId").val());
            var cell3 = ($("#myTable #mycustomtitle").val());
            var cell4 = ($("#myTable #mycustomedit").val()); 

            $("#myTable tr:eq(" + (indx) + ") td:eq(0)").html(cell1);
            $("#myTable tr:eq(" + (indx) + ") td:eq(1)").html(cell2);
            $("#myTable tr:eq(" + (indx) + ") td:eq(2)").html(cell3);
            $("#myTable tr:eq(" + (indx) + ") td:eq(3)").html(cell4);
            $("#myTable tr:eq(" + (indx) + ") td:eq(4)").find('#cancelBtn').remove();
        }



    </script>
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.