16

How can I use jQuery to click on a table cell and edit its contents. There is a particular column which contains several paragraphs of data, so if possible, have a pop up window with a large text area (or ideally an HTML editor).

The changes need only be superficial as I am using another jQuery plugin to scrape the table contents and export it to something else.

Difficulty, none of the cells can have unique names or id's.

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
mrpatg
  • 10,001
  • 42
  • 110
  • 169

10 Answers10

14

Seeing as how this page is both 3 years old and the first result in a Google search I thought it was due a more current answer. Given the weight and complexity of the plugin options above I thought a simpler, no-frills, more direct solution might also be appreciated for those looking for alternatives.

This replaces the table cell with a text input and calls custom events so you can handle whatever use case you want on save, close, blur, etc...

In this case the only way to change the information in the cell is to press enter, but you can customize that if you like, eg. you might want to save on blur.

In this example you can also press the Esc key to stop editing and put the cell back to what it was. You can customize that if you like.

This example works on a single click, but some people prefer doubleclick, your choice.

$.fn.makeEditable = function() {
  $(this).on('click',function(){
    if($(this).find('input').is(':focus')) return this;
    var cell = $(this);
    var content = $(this).html();
    $(this).html('<input type="text" value="' + $(this).html() + '" />')
      .find('input')
      .trigger('focus')
      .on({
        'blur': function(){
          $(this).trigger('closeEditable');
        },
        'keyup':function(e){
          if(e.which == '13'){ // enter
            $(this).trigger('saveEditable');
          } else if(e.which == '27'){ // escape
            $(this).trigger('closeEditable');
          }
        },
        'closeEditable':function(){
          cell.html(content);
        },
        'saveEditable':function(){
          content = $(this).val();
          $(this).trigger('closeEditable');
        }
    });
  });
return this;
}

You can selectively apply the editable cells by attaching them like so, or whatever makes sense for your case.

$('.editable').makeEditable();
Ahmed Ashour
  • 5,179
  • 10
  • 35
  • 56
Strixy
  • 568
  • 5
  • 15
  • This does not work for me -- something as simple as `$('td').makeEditable();` does not make any cell in the one table I have on the page editable. – jimiayler Feb 05 '16 at 14:54
12

I use Data tables (a jQuery plugin) as this makes everything so much simpler.

They also say to use the jEditable plugin with their plugin. Allows for rows to become editable: Link: Editable Table (includes code sample)

Andrew
  • 896
  • 2
  • 12
  • 31
8

Try this simple solution:

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

        var inputNewText = prompt("Enter new content for:", OriginalContent);

        if (inputNewText != null) {
            $(this).text(inputNewText)
        }
    });
});
Ahmed Ashour
  • 5,179
  • 10
  • 35
  • 56
markouuu
  • 121
  • 2
  • 9
6

You may want to check the jqGrid plugin.

Daniel Moura
  • 7,816
  • 5
  • 35
  • 60
3

jEditable plugin can help you edit your table in place.

$(document).ready(function() {
    $('td').editable('http://www.example.com/save.php');
});
RaYell
  • 69,610
  • 20
  • 126
  • 152
3

Making content editable can be achieved with plugins like the jQuery Editable one. How easy this would be to translate onto a table with no ids though, I'm not sure.

To traverse your table (and I'm assuming your table either has an ID of its own or is the only table on the page) would be reasonably straight-forward if you were able to get that plugin working:

$('#myTable td').editable();

But that doesn't give you the rich text editor you're after. The other approach would be to forget that plugin and try using the jQuery UI dialog.

$('#myTable td').click(function(){
  $('myDialog').dialog('open');
});

Assuming you put a rich-text editor in that dialog, you could use $.ajax() to post the result to some service at the server end.

Finally, the jqGrid might be a good option for you, depending on the data that you want in your table.

Phil.Wheeler
  • 16,748
  • 10
  • 99
  • 155
2

Inkedmn's code not functional as it is but it is the simplest way to do it as an idea: So check out the following working code based on his logic:

$(function() {
    $('#overlay').hide();
    $('td').click(function(event) {
        var myText = '';
        $('#overlay').show();
        var o = $(this);
        $('#closeLink').click(function(event) {
            event.preventDefault();
            myText = $('#overlay textarea').val();
            $(o).html(myText);
            $(this).parent().hide(500);
        });                  
    });
});
Ahmed Ashour
  • 5,179
  • 10
  • 35
  • 56
Murat Kazanova
  • 329
  • 1
  • 3
  • 10
1

The JQuery Datatables Editable plugin seems to be better than the official Editable Table plugin, because the former supports in-line editing and is open-source.

HRJ
  • 17,079
  • 11
  • 56
  • 80
1
$("td").click(function(event){
    var myText = '';
    $("myOverlayThing").show();
    $("myOverlayThingCloseLink").click(function(event){
        event.preventDefault();
        myText = $("myOverlayThing.textarea").val();
    });
    $(this).html(myText);
});

Probably a little more complicated than that, but that's the basic idea without seeing your HTML.

brettkelly
  • 27,655
  • 8
  • 56
  • 72
1

this is actually so straight forward, this is my HTML, jQuery sample.. and it works like a charm, I build all the code using an online json data sample. cheers

<< 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>
Mahmoud Sayed
  • 151
  • 2
  • 10