4

I need to update a row of a table. So when I click on a cell, I want it to be transformed into text box, so I used this:

<td contenteditable></td>

And then, when the content of a <td> is changed, I need to send it through AJAX to update it in the server without clicking on a button, so it will use the .change(function()).

I tried to get the content changed into a variable:

$("TD").change(function()
{
//Here I want to set the row ID:
var rowid = '<?php echo $row['id'] ?>';
var name = $("#emp_name").val();
var position = $("#position").val();
var salary = $("#salary").val();
$.ajax
        ({
            url: 'update.php', 
            type: 'POST', 
            data: {dataId: rowid, data1: name, data2: position, data3: salary},//Now we can use $_POST[data1];
            dataType: "text",

            success:function(data)
            {
                if(data=="success")
                {
                    //alert("Data added");
                    $("#before_tr").before("<tr><td>"+emp+"</td><td>"+pos+"</td><td>"+sal+"</td></tr>");
                    $("#emp_name").val("");
                    $("#position").val("");
                    $("#salary").val("");
                }
            },

            error:function(data)
            {
                if(data!="success")
                {
                    alert("data not added");
                }
            }

        });
});

The problem is how to know which row is changed to send it via AJAX ? I am not getting any errors even when data not updated.

Here is the update.php code:

try
{
        $rowid = $_POST['dataId'];
        $emp_name = $_POST['data1'];
        $pos = $_POST['data2'];
        $sal = $_POST['data3'];

        $upd = "UPDATE emp SET name = :emp_name, position = :pos, sal = :sal WHERE id  = :rowid";
        $updStmt = $conn->prepare($upd);
        $updStmt->bindValue(":rowid", $rowid);
        $updStmt->bindValue(":emp_name", $emp_name);
        $updStmt->bindValue(":pos", $pos);
        $updStmt->bindValue(":sal", $sal);
        $updStmt->execute();

        echo "success";
}

catch(PDOException $ex)
{
    echo $ex->getMessage();
}

HTML:

<tbody>
                <?php
                $sql = "SELECT * FROM employee";
                $stmt=$conn->prepare($sql);
                $stmt->execute();
                $res=$stmt->fetchAll();
                foreach($res as $row){
                ?>
                <tr id=""<?php echo $row['id'] ?>"">
                    <td contenteditable><?php echo $row['emp_name'] ?></td>
                    <td contenteditable><?php echo $row['position'] ?></td>
                    <td contenteditable><?php echo $row['salary'] ?></td>
                </tr>
                <?php } ?>

2 Answers2

1
<tr row_id="<?php echo $row['id'] ?>"> ></tr>

In Your Ajax

var rowid = $(this).attr('row_id');
santosh
  • 799
  • 5
  • 17
1

When loading your data with PHP you need to keep the row id in your html:

<tr id="<?php echo $yourList["id"]; ?>">
<td contenteditable></td>
</tr>

Then in your javascript you can catch it using the parent() jquery function

$("TD").change(function()
{
//Here I want to set the row ID:
var rowid =$(this).parent().attr("id");

......

UPDATE

Check this example, I have added listeners to detect contenteditable td changes, I think you shall add it too , refer to this contenteditable change events for defining proper change events on contenteditable fields.

Explanation:

The contenteditable does not trigger change events, this work around is used to detect the focus event of the td using jquery on method and event delegation. The original content is saved in the td jquery data object $this.data('before', $this.html()); . Then when the user leaves the field or triggers any of the events 'blur keyup paste input', the current content is compared to the content in the data object, if it differs, the change event of the td is triggered.

$(document).ready(function(){

  
  $('table').on('focus', '[contenteditable]', function() {
    var $this = $(this);
    $this.data('before', $this.html());
    return $this;
  }).on('blur keyup paste input', '[contenteditable]', function() {
    var $this = $(this);
    if ($this.data('before') !== $this.html()) {
        $this.data('before', $this.html());
        $this.trigger('change');
    }
    return $this;
  });
  
  $("TD").change(function()
  {
    //Here I want to set the row ID:
    var rowid = $(this).parent().attr("id");

    $("#res").html(rowid);
  });

});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<table border="1" width="500px">
  <tr  id="1222">
    <td contenteditable></td>
  </tr>
  
  <tr  id="55555">
    <td contenteditable></td>
  </tr>
  
 </table>

Row Id : <span id="res"></span>
Community
  • 1
  • 1
KAD
  • 10,972
  • 4
  • 31
  • 73
  • I tried it and try to see the id in the console but nothing appeared –  Feb 02 '16 at 08:45
  • show me the html generated after adding the id attribute to the `tr` – KAD Feb 02 '16 at 08:46
  • I will add the html in my question –  Feb 02 '16 at 08:47
  • `""> ` is wrong, it must be `` – KAD Feb 02 '16 at 08:48
  • still can't see the id, the result of `console.log(rowid);` is none –  Feb 02 '16 at 08:50
  • with the devtools, inspect the `tr` line and make sure there is a valid id value, please post the markup you see – KAD Feb 02 '16 at 08:51
  • Still the same, empty result in the console, I tried `$("TR")` instead of `$("TD") and still the same –  Feb 02 '16 at 08:53
  • it works, but can you explain in details what happened in the listener (from `$('table')...`) –  Feb 02 '16 at 09:06
  • 2
    The contenteditable does not trigger change events, this work around is used to detect the `focus` event of the td using jquery `on` method and event delegation. The original content is saved in the `td`jquery data object $this.data('before', $this.html());. Then when the user leaves the field or triggers any of the events `'blur keyup paste input'`, the current content is compared to the content in the data object, if it differs, the change event of the `td` is triggered. – KAD Feb 02 '16 at 09:10