0

I'm trying to make a dynamic table with variable no. of rows and columns. Table is created but when i click on the cells, they are not editable as i assumed they will be.

$(document).ready(function() {
            $("#createit").click(function() {
                var num_rows = document.getElementById('rows').value;
                var num_cols = document.getElementById('cols').value;
                var tbody = '';
                for (var i = 0; i < num_rows; i++) {
                    tbody += '<tr>';
                    for (var j = 0; j < num_cols; j++) {
                        tbody += '<td tabindex=' + j + '>';
                        tbody += 'Cell' + i + j;
                        tbody += '</td>'
                    }
                    tbody += '</tr>';
                }
                //document.getElementById('wrapper').innerHTML = theader + tbody + tfooter;
                $('.editableTable').append(tbody);
            });
        });
        $(".editableTable td").dblclick(function() {
            console.log('clicked');
            var OriginalContent = $(this).text();
            $(this).addClass("cellEditing");
            $(this).html("<select><option>1</option><option>2</option><option >3</option></select>");
            $(this).children().first().focus();
            $(this).bgColor = 'red';

            $(this).children().first().keypress(function(e) {
                if (e.which == 13) {
                    var newContent = OriginalContent;
                    $(this).parent().text(OriginalContent);
                    $(this).parent().removeClass("cellEditing");
                }
            });
            $(this).children().first().blur(function() {
                $(this).parent().text(OriginalContent);
                $(this).parent().removeClass("cellEditing");
            });
        });
        $(".editableTable td").bind('keydown', function(event) {
            if (event.keyCode === 9 || event.keyCode === 13) {
                var tabindex = $(this).attr('tabindex');
                tabindex++; //increment tabindex
                $('[tabindex=' + tabindex + ']').focus().dblclick();
                return false;
            }
        });
.editableTable {
            border: solid 0px;
            width: 100%;
            text-align: center
        }

        .editableTable td {
            border: solid 0.5px;
            border-color: lightblue;
            min-width: 100px;
        }

        .editableTable .cellEditing {
            padding: 0;
        }

        select {
            border: 0px;
            width: 100%;
        }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<label>Rows: <input type="text" name="rows" id="rows"/></label><br />
    <label>Cols: <input type="text" name="cols" id="cols"/></label><br/>
    <input name="generate" type="button" value="Create Table!" id='createit' />
    <div id="wrapper">
        <table class="editableTable">
            <tbody></tbody>
        </table>
    </div>

Same thing i have done before but with a static table. JSFIDDLE https://jsfiddle.net/rbrohitbisht/691rx62k/

Now i want to do the same thing with the dynamic table. What i'm doing wrong here?

Rabinder Bisht
  • 584
  • 2
  • 7
  • 19

4 Answers4

0

The operation should be moved into the createit handler definition.

 $(".editableTable td").dblclick(function() {...});

Just after the cells are created(of course after a click on Crete Table!).

Otherwise the selector $(".editableTable td") would not return anything before the dynamic table is in place.

Rajeev Ranjan
  • 3,588
  • 6
  • 28
  • 52
  • This solved my problem. But I have one doubt, I'm calling $(".editableTable td") only when some 'td' is dblclicked, So, that means only after table creation, After all, I can click on table cell only after the creation of the table. So logically it should work with $(".editableTable td").dblclick(function(){});. Or it is working like, at the loading of js, if it didn't find any class with this name then it will return nothing? – Rabinder Bisht Jun 05 '17 at 20:10
  • $(".editableTable td").dblclick(..) is called on document load that is initially. At that moment, the selector returns nothing. So, the event handler is not attached to anything at all. To go on to understand things better, try running this piece of code in firebug after, the table is created. Once you run this code, you will get to see what all elements the handler was attached to. Run the same without a table created. You will get to see the difference. – Rajeev Ranjan Jun 06 '17 at 02:53
0

You should add contenteditable="true" to your code

https://codepen.io/anon/pen/XgJaxE

$(document).ready(function() {
        $("#createit").click(function() {
            var num_rows = document.getElementById('rows').value;
            var num_cols = document.getElementById('cols').value;
            var tbody = '';
            for (var i = 0; i < num_rows; i++) {
                tbody += '<tr>';
                for (var j = 0; j < num_cols; j++) {
                    tbody += '<td contenteditable="true" tabindex=' + j + '>';
                    tbody += 'Cell' + i + j;
                    tbody += '</td>'
                }
                tbody += '</tr>';
            }
            //document.getElementById('wrapper').innerHTML = theader + tbody + tfooter;
            $('.editableTable').append(tbody);
        });
    });
    $(".editableTable td").dblclick(function() {
        console.log('clicked');
        var OriginalContent = $(this).text();
        $(this).addClass("cellEditing");
        $(this).html("<select><option>1</option><option>2</option><option >3</option></select>");
        $(this).children().first().focus();
        $(this).bgColor = 'red';

        $(this).children().first().keypress(function(e) {
            if (e.which == 13) {
                var newContent = OriginalContent;
                $(this).parent().text(OriginalContent);
                $(this).parent().removeClass("cellEditing");
            }
        });
        $(this).children().first().blur(function() {
            $(this).parent().text(OriginalContent);
            $(this).parent().removeClass("cellEditing");
        });
    });
    $(".editableTable td").bind('keydown', function(event) {
        if (event.keyCode === 9 || event.keyCode === 13) {
            var tabindex = $(this).attr('tabindex');
            tabindex++; //increment tabindex
            $('[tabindex=' + tabindex + ']').focus().dblclick();
            return false;
        }
    });
RouthMedia
  • 401
  • 1
  • 4
  • 17
  • as I have already stated what I'm trying to do, and also referred one JSFIDDLE, I don't need to make it contenteditable="true", but now i got the answer, thanks for you time and response. https://codepen.io/anon/pen/owgyqg#anon-login – Rabinder Bisht Jun 05 '17 at 19:59
0

use HTML DOM "contentEditable" Property Element Object https://stackoverflow.com/a/44380264/3615816

<input type=button value="Enable editing"
onclick="document.getElementById('t1').contentEditable = 'true';alert('You can now edit table')" />

<table id="t1"   border="1">
 
  <tr><td >c1</td><td >c2</td></tr>
  <tr><td >cc1</td><td >cc2</td></tr>

</table>

<input type=button value="disable editing"
onclick="document.getElementById('t1').contentEditable = 'false'; " />
Hossein Hajizadeh
  • 1,357
  • 19
  • 10
  • Thanks for ur response but this is not that one what I'm looking for... – Rabinder Bisht Jun 05 '17 at 20:01
  • Dear friend. I am aware of your question, and this is a complementary code snippet for your code and automatically created for the table to edit it, you can use this code – Hossein Hajizadeh Jun 06 '17 at 01:25
  • First thing, a table cell must be editable only when a cell is clicked. The editable cell may contain option-select, text-box etc. While editing a cell, when a tab pressed, it should focus next tab-index cell and make it editable. Last thing, the original value of the cell should be retained and the value selected from the dropdown will be used for further things. – Rabinder Bisht Jun 06 '17 at 04:22
0

 $(document).ready(function () {
        $("#createit").click(function () {
            var num_rows = document.getElementById('rows').value;
            var num_cols = document.getElementById('cols').value;
            var tbody = '';
            var tabindex = 0
            for (var i = 0; i < num_rows; i++) {
                tbody += '<tr>';
                for (var j = 0; j < num_cols; j++) {
                    tbody += '<td tabindex=' + tabindex++ + '>';
                    tbody += 'Cell' + i + j;
                    tbody += '</td>'
                }
                tbody += '</tr>';
            }
            //document.getElementById('wrapper').innerHTML = theader + tbody + tfooter;
            $('.editableTable').append(tbody);
        });
    });
    $(document).on('dblclick', 'td', function () {
        console.log('clicked');
        this.contentEditable = 'true';
    });
    $(document).on('keydown', 'td', function (event) {
        if (event.keyCode === 9 || event.keyCode === 13) {
            this.contentEditable = 'false';
            //  $(this).next().focus().dblclick().focus();
            var tabindex = $(this).attr('tabindex');
            tabindex++;
            var next = $('[tabindex=' + tabindex + ']').focus().dblclick();
            if (next.is('td') == false)
                return true;
            var sel, range;
            if (window.getSelection && document.createRange) {
                range = document.createRange();
                range.selectNodeContents(next[0]);
                range.collapse(true);
                sel = window.getSelection();
                sel.removeAllRanges();
                sel.addRange(range);
            } else if (document.body.createTextRange) {
                range = document.body.createTextRange();
                range.moveToElementText(next[0]);
                range.collapse(true);
                range.select();
            }

            return false;
        }
    });
.editableTable {
            border: solid 0px;
            width: 100%;
            text-align: center
        }

        .editableTable td {
            border: solid 0.5px;
            border-color: lightblue;
            min-width: 100px;
        }

        .editableTable .cellEditing {
            padding: 0;
        }

        select {
            border: 0px;
            width: 100%;
        }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<label>Rows: <input type="text" name="rows" id="rows"/></label><br />
    <label>Cols: <input type="text" name="cols" id="cols"/></label><br/>
    <input name="generate" type="button" value="Create Table!" id='createit' />
    <div id="wrapper">
        <table class="editableTable">
            <tbody></tbody>
        </table>
    </div>
Hossein Hajizadeh
  • 1,357
  • 19
  • 10