fnAddData not working as expected

fnAddData not working as expected

chris_nchris_n Posts: 53Questions: 3Answers: 0
edited September 2011 in DataTables 1.8
I have a table which gets and posts data serverside. The table is setup to be editable using jEditable. I am attempting to use fnAddData to add rows to the table. However, the call to fnAddData seems to result in nothing even though no errors are encountered. Stepping through the JS inside firebug reveals no errors or unexpected code behavior. But the new row never appears in the browser. aoData does increment with each execution of fnAddData, so it does appear that the table object gets a row added.

Any help will be greatly appreciated!

Chris

My code looks like this:

[code]
//<![CDATA[
function jEdit(oTable) {
}

var oTable;

$(document).ready(function(){

oTable = $("#order").dataTable( {
"bProcessing": true,
"bServerSide": true,
"bAutoWidth" : false,
"bPaginate": false,
"bFilter": false,
"bSort": false,
"bInfo": false,
"sAjaxSource": "http://foobar.com/order/table",
"aaSorting" : [[0, "desc"]],
"aoColumns": [
{ "sWidth": "5px" },
{ "sWidth": "5px" },
{ "sWidth": "25px" },
{ "sWidth": "75px" },
{ "sWidth": "10px" },
{ "sWidth": "10px" },
{ "sWidth": "10px" },
],
"fnDrawCallback": function() {
/* Apply the jEditable handlers to the table */
$('#order tbody td').editable( "http://foobar.com/order/table_edit", {
"callback": function( sValue, y ) {
/* alert('sValue = ' + sValue + '; y = ' + y); */
var aPos = oTable.fnGetPosition( this );
oTable.fnUpdate( sValue, aPos[0], aPos[1] );
},
"submitdata": function ( value, settings ) {
return {
"stock_num": this.parentNode.getAttribute('id'),
"column": oTable.fnGetPosition( this )[2],
"order_num": $('#order_num').html(),
};
},
"height": "14px"
} );
},
"fnRowCallback": function( nRow, aData, iDisplayIndex ) {
/* alert('nRow = ' + nRow + '; aData = ' + aData + '; iDisplayIndex = ' + iDisplayIndex); */
if ( aData[7] >= 0 )
{
$('td:eq(7)', nRow).attr("class","currency");
}
$(nRow).attr("id", aData[1]);
return nRow;
},
"fnFooterCallback": function (nRow, aaData, iStart, iEnd, aiDisplay ) {
/* alert('iStart = ' + iStart + 'iEnd = ' + iEnd + 'aaData length = ' + aaData.length); */


/* A function to format currency properly; Found here: */
/* http://www.selfcontained.us/2008/04/22/format-currency-in-javascript-simplified/ */
function formatCurrency(num) {
num = isNaN(num) || num === '' || num === null ? 0.00 : num;
return parseFloat(num).toFixed(2);
}

/* Calculate the total order cost if the order exceeds a single page*/
if (aaData.length > iEnd) {
var iOrderTotalCost = 0;
for ( var i=0; i

Replies

  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    I just realized I forgot to post the associated HTML, so here it is:

    [code]





    Item
    Stock Number
    Description
    Notes
    Quantity
    UOM
    Ext Cost (Avg)




    Total:
    $0.00 ($0.00 total)




    Row 1
    Row 2
    Row 3
    Row 4
    Row 5
    Row 6
    Row 7

    <!-- DataTables jQuery builds the table body -->


    <!-- container -->
    <!-- data_table -->
    [/code]
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    edited September 2011
    is the data getting posted to another page in your datatable (i.e. not visible in current pagination)?
  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    In this case there are only two records total so no chance of that, unfortunately.

    I notice that aiDisplay also gains an element with each call of fnAddData as well, so the underlying logic appears to be working, just not the display of the new row.
  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    edited September 2011
    Well it does not even work with this simple configuration. Is there a possible bug in Datatables here?

    [code]
    //<![CDATA[
    var oTable;

    $(document).ready(function(){

    oTable = $("#order").dataTable( {
    "bProcessing": true,
    "bServerSide": true,
    "bAutoWidth" : false,
    "bPaginate": false,
    "bFilter": false,
    "bSort": false,
    "bInfo": false,
    "sAjaxSource": "[% c.uri_for('/order/table') %]", /* Template Toolkit URI reference */
    "aaSorting" : [[0, "desc"]],
    "aoColumns": [
    { "sWidth": "5px" },
    { "sWidth": "5px" },
    { "sWidth": "25px" },
    { "sWidth": "75px" },
    { "sWidth": "10px" },
    { "sWidth": "10px" },
    { "sWidth": "10px" },
    ] } );

    } );

    function fnClickAddRow() {
    var aoData = oTable.fnAddData( [
    "3",
    "3",
    "Milk",
    "From brown cows eating green grass",
    "3",
    "gal",
    "3.98" ], false );
    var oSettings = oTable.fnSettings();
    alert("Start = " + oSettings._iDisplayStart + "; Length = " + oSettings._iDisplayLength + "; aiDisplay = " + oSettings.aiDisplay);
    alert("aoData = " + aoData);
    };
    //]]>
    [/code]
  • allanallan Posts: 63,494Questions: 1Answers: 10,470 Site admin
    > "bServerSide": true

    This doesn't really play well with fnAddData - indeed not at all, since DataTables doesn't know anything about your data source - its all server-side. So what is happening is that fnAddData does add the data, on the client-side, then it requests a redraw, and since your server knows nowthing of this, it just gives back the old data!

    So what you really need to do is not use fnAddData, but rather make an Ajax call to your server to add the data to whatever your data source is (an SQL DB?) and then call fnDraw() to load in the new data.

    I'm going to go right now and add a note to the documentation for fnAddData :-)

    Allan
  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    But that does not seem to agree with the fnAddData docs which state concerning the second optional parameter passed in:

    boolean : optional - redraw the table or not after adding the new data (default true)

    I have set it as false to prevent the redraw request.

    Maybe explaining what I'm trying to accomplish will help. Perhaps I'm chasing the wrong rabbit. ;-)

    I want to add a blank row to the table and the have the user populate it (hence jEditable) and allow jEditable to post the data back serverside where it will be pushed into the back-end database.

    Kind Regards,
    Chris
  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    Incidentally, setting bServerSide:false still does not result in a row being added.
  • allanallan Posts: 63,494Questions: 1Answers: 10,470 Site admin
    If you set the second parameter to false so there is no redraw though, then the table isn't going to get redrawn to show your new row :-). The row would only get added when the table does a redraw - hence why fnAddData is incompatible (or rather pointless) with server-side processing.

    > I want to add a blank row to the table and the have the user populate it (hence jEditable) and allow jEditable to post the data back serverside where it will be pushed into the back-end database.

    Got it! Don't use fnAddData then :-). Just do a standard DOM appendChild() to the table's TBODY with your new row that you've created. That way you are manipulating the DOM directly yourself, and putting in what you need. When you save it to the server, just call fnDraw and all will be right with the world (or at least a little closer!).

    The one thing to watch with this is if the table does a redraw (i.e. a sort or filter or anything else) with your own element in there, it will be removed as part of the redraw. You might need to store it in a variable somewhere and use fnDrawCallback to readd it if it gets removed in this way.

    Allan
  • chris_nchris_n Posts: 53Questions: 3Answers: 0
    Thanks for the pointer, Allan. I'll give appendChild() a spin, and see if I can make things work with it.

    Thanks as well for this fantastic tool!

    Kind Regards,
    Chris
This discussion has been closed.