How to reinitialize a datatable

How to reinitialize a datatable

MinervaMinerva Posts: 22Questions: 0Answers: 0
edited August 2011 in DataTables 1.8
I have a dataTable that is populated without issue when the page loads. Very slick. Love clicking the column names to sort.

The wrinkle is... the user can specify a different date range, and I'd like to repopulate the dataTable at that point. I call the same function as when the page loads and attempt to repopulate the dataTable object. I am learning it is not so easy to blow away and reload the dataTable. I am doing this in PowerChart so I don't have a public facing page that I can show you. However, I'd be glad to provide additional code or information that may be helpful.

HTML:
[code]



Event ID
Date
Subject
Result











[/code]

NOTE: The #documents table populates fine (on the initial load of the page) without the THEAD and TBODY tags, if that is a clue to my puzzle.

.JS FILE:
[code]
var oTable = $('#documents').dataTable({
"aoColumns": [
{ "sTitle": "EventID", "bVisible": false },
{ "sTitle": "Date", "sWidth": "110px", "bSortable": true },
{ "sTitle": "Subject", "sWidth": "270px", "bSortable": true },
{ "sTitle": "Result", "sWidth": "100px", "bSortable": true }],
"bRetrieve": true,
"bProcessing": true,
"bDestroy": true,
"bPaginate": false,
"bAutoWidth": false,
"bFilter": false,
"bInfo": false,
"aaSorting": [[1, 'desc']],
"bJQueryUI": false
});
[/code]

Currently I don't get an error but the dataTable does not repopulate.

Setting bServerSide to True put me in an endless loop ("DataTables warning: JSON data from server failed to load or be parsed. This is most likely to be caused by a JSON formatting error")

I am using jquery.dataTables.min.js version 1.8.1. I was hoping that setting bDestroy to True would put me on the right path but this is still vexing me. Thank you for any ideas.

Replies

  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    edited August 2011
    (fixed the code formatting)
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    What is your data source?

    also, if you use bRetrieve: true, it doesn't initialize anything, only returns the Table as a JQuery object.
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    Hi fbas.
    The datasource is XMLCclRequest(), which is XMLHttpRequest() as it is called by mPagesJS.

    mPagesJS is a jquery library created for Cerner PowerChart (http://www.mpagesjs.org/)
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    edited August 2011
    entire code routine:
    [code]
    function DocumentsTable(fromDate, toDate) {

    if (fromDate !== 0) {
    // if we are working with dates, make them date data type instead of strings:
    var documentFrom = new Date(fromDate);
    var documentTo = new Date(toDate);
    }
    else {
    // put the vanilla zeroes into the documentFrom, documentTo variables this routine uses:
    var documentFrom = 0;
    var documentTo = 0;
    };

    // Initialize the request object:
    var DocumentInfo = new XMLCclRequest();

    // When our request object has changed:
    DocumentInfo.onreadystatechange = function () {

    if (DocumentInfo.readyState == 4 && DocumentInfo.status == 200) {

    // Convert returned string to JSON object (eval):
    var msgDoc = DocumentInfo.responseText;
    if (msgDoc !== undefined && msgDoc !== null) {
    var jsonDoc = eval("(" + msgDoc + ")");
    }

    if (jsonDoc && jsonDoc.DATAREC.LIST) {

    var oTable = $("#documents").dataTable({
    "aoColumns": [
    { "sTitle": "EventID", "bVisible": false},
    { "sTitle": "Date", "sWidth": "110px", "bSortable": true},
    { "sTitle": "Subject (click any column name to sort)", "sWidth": "270px", "bSortable": true},
    { "sTitle": "Result", "sWidth": "100px", "bSortable": true}
    ],
    "bProcessing": true,
    "bDestroy": true,
    "bPaginate": false,
    "bAutoWidth": false,
    "bFilter": false,
    "bInfo": false,
    "aaSorting": [[1, 'desc']],
    "bJQueryUI": false
    }); // end var oTable definition

    // append each row to the oTable datatable:
    for (var i = 0; i < jsonDoc.DATAREC.LIST.length; i++) {

    oTable.fnAddData([
    //event_ID is not visible to the user:
    jsonDoc.DATAREC.LIST[i].EVENT_ID,
    jsonDoc.DATAREC.LIST[i].EVENT_DT,
    jsonDoc.DATAREC.LIST[i].EVENT_TITLE_TEXT,
    jsonDoc.DATAREC.LIST[i].EVENT_RESULT
    ]);
    } // end for loop

    } //end if (jsonDoc &&...

    else
    // We don't have any data to work with:
    { $('#documents').html('No Documents Found')}

    }; //end if (DocumentInfo.readyState === 4 &&...

    } //end DocumentInfo.onreadystatechange

    // Call the ccl progam and send the parameter string:
    DocumentInfo.open("GET", "MPAGE_DOC");

    if (documentFrom === 0) {
    // the initial trip through, we pass in zeroes instead of dates:
    DocumentInfo.send("^MINE^, value($VIS_Encntrid$), value($PAT_Personid$), ^0^,^0^");
    }
    else
    {
    // user has selected dates so format them for the CCL request:
    DocumentInfo.send("^MINE^, value($VIS_Encntrid$), value($PAT_Personid$), ^" + documentFrom.format('mmddyyyy') + "^,^" + documentTo.format('mmddyyyy') + "^");
    };
    return;

    } //end DocumentsTable ()
    [/code]
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    You might not need to repopulate the table (if the initial data is the entire set) but simply run a date range filter on it.

    In order to do this, you would need to run your JSON code, then create a Table object with the data (rather than filling in oTable.fnAddData) then run the intialization just once. After that you can use a range filtering plugin function. http://datatables.net/release-datatables/examples/plug-ins/range_filtering.html

    ----

    Did removing the bRetrieve not fix your existing code?
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    Unfortunately the initial data is not the entire set. This could potentially be a very large set of documents, so we're initially returning the top 50. The date range filter will likely be used if the user wants to go much farther back in the patient's history.

    Removing bRetrieve did not alter how the code runs.

    I'm really stumped on this one. Should I look into returning the entire set and then applying a filter on it for display? Is there really no way to wipe the dataTable out and start over? I'm willing to try anything at this point.

    Thank you for your help.
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    Update: I looked into returning all the data and that is not a good solution for us.

    Is using a datatable the wrong route here if I need to reload it and display new results? Maybe I should take a different route than a datatable? I love the column sorting and how the datatable looks/acts, but I have to be able to reload it with new results.

    It seems like it should be so simple. All ideas welcome.
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    when I get a chance later today, I'll try to set up your code and see what I can find.
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    I would really appreciate that. Another set of eyes (and another brain) would be so helpful.

    If I can provide any other detail, I'd be glad to. I wish I had a public facing page so I could provide a link.
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    Can you provide a link to your project, or clue me in as to what xmlcclrequest is all about? I installed the library but since I don't know what it does, I don't know how to negotiate the errors to get things set up so I can get your code going.
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    I am working on Cerner PowerChart, building custom pages in the patient chart (called MPages).

    The Mpages jquery library (mpagesjs) provides the xmlcclrequest object, which is its version of XMLHttpRequest.

    Here is a bit more about it: http://plugins.jquery.com/plugin-tags/xmlcclrequest

    Hope this helps. Would be glad to provide any information I can. I appreciate your time.
  • fbasfbas Posts: 1,094Questions: 4Answers: 0
    You've got a lot of weird custom stuff in there (Date.format() which I was able to find, and anchor.click() inside the xmlcclrequest.js code which I don't know what this refers to) I can't run the code. it would be best if I could get a link to your project.
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    The date.format thing is a little goofy. The first time we run the code, when the page loads, we pass zeroes to the CCL request that returns the data set. Subsequent passes through this function use dates that the user specifies.

    The mpagesjs library (which contains XMLCclRequest) is included in PowerChart at a level above my pages (in other words, it is not a .js file I include at the top of the html with the rest of the .js and .css file references). I am wondering if the code it contains will function/make any sense if I try to pull all my code to provide a link to you somewhere, or if it's so specific to PowerChart that it won't help to do so?

    Maybe I'm coming at this from the wrong angle. Is it a bad idea to try to do what I'm trying to do with dataTables? It seems like a logical thing to do from my vantage point but my background is more Visual Basic. I had no idea attempting to repopulate a datatable would cause such excitement. All thoughts welcome.
  • pgalganopgalgano Posts: 6Questions: 0Answers: 0
    Not familiar with the exact jquery stuff you are using but I have a table that I reinit and repopulate with new json data from the backend as a result of new search criteria. The following are the important peices of it.

    Helper method that I add to datatables to be able to turn ona nd off processing indicator

    [code]
    /*
    * Register a new feature with DataTables
    */
    if ( typeof $.fn.dataTable == "function" &&
    typeof $.fn.dataTableExt.fnVersionCheck == "function" &&
    $.fn.dataTableExt.fnVersionCheck('1.7.4') )
    {
    $.fn.dataTableExt.oApi.fnProcessingIndicator = function ( oSettings, onoff )
    {
    if( typeof(onoff) == 'undefined' )
    {
    onoff=true;
    }
    this.oApi._fnProcessingDisplay( oSettings, onoff );
    }

    $.fn.dataTableExt.oJUIClasses.sProcessing="dataTables_processing ui-state-highlight";

    }
    else
    {
    alert( "Warning: SearchForm requires DataTables 1.7.4 or greater - www.datatables.net/download");
    }
    [/code]

    Code that hooks to the jquery XMLHttpRequest event handlers for pre and post processing that handle table reset and population. The key part for reseting the datatable is the call to fnClearTable.

    [code]

    function processData(data)
    {
    //clear the table again in the case of a double submit
    datatable.fnClearTable();
    //add data to table
    datatable.fnAddData(data);
    //turn off processing indicator
    datatable.fnProcessingIndicator(false);
    }

    // pre-submit callback
    function preRequest(formData, jqForm, options) {
    //turn on procesing indicator
    datatable.fnProcessingIndicator(true);
    //clear table
    datatable.fnClearTable();
    return true;
    }
    [/code]
  • MinervaMinerva Posts: 22Questions: 0Answers: 0
    Update! This is now working. It turns out that the dataTable definition was ready to roll with the bDestroy property as well as this little snippet:

    [code]
    if (oTable != undefined) {
    oTable.fnClearTable();
    };
    [/code]

    One wrinkle that wasn't obvious... If you are using a dialog box to collect your new date parameters, its modal property can interfere with the firing of your function to repopulate the data table. Who knew?

    Thanks everyone for your help and time on this. It is appreciated.
  • zeddarnzeddarn Posts: 1Questions: 0Answers: 0
    Found this solutions that worked perfect Click
  • michelkoganmichelkogan Posts: 4Questions: 0Answers: 0
    can you explain more? I have the same problem here. Where did you add that little snippet ?
  • naidnaid Posts: 1Questions: 0Answers: 0
    edited September 2012
    This works:

    [code]
    var oTable = $('#tableID').dataTable();
    oTable.fnDestroy();

    //I put in new values 'newList' on the body
    $('#tableID tbody').html(newList);

    //I reinitialize the datatable
    $('#tableID').dataTable({"oLanguage": { "sSearch": 'Search Contacts:' }});
    [/code]

    This works for me and I now have real time recomputation of the rows, values, pagination, etc
  • tommy007tommy007 Posts: 1Questions: 0Answers: 0
    Thanks works well.

    Just don't forget to delete the existing rows from the table.
    I do this after the call to fnDestroy.
  • gustinmigustinmi Posts: 1Questions: 0Answers: 0
    If you have server side data, this is the only working solution:

    Extension function


    $.fn.dataTableExt.oApi.fnReloadAjax = function (oSettings, sNewSource, myX1, myX2 )
    {
    if ( oSettings.oFeatures.bServerSide ) {
    oSettings.aoServerParams = [];
    oSettings.aoServerParams.push({"sName": "user",
    "fn": function (aoData) {
    aoData.push(
    {"name": "myX1name", "value": myX1},
    {"name":"myX2name", "value": myX2}
    );
    }});

    this.fnClearTable(oSettings);
    this.fnDraw();
    return;
    }
    };



    On change handler



    if (oTable == null) {
    oTable = $(".items").dataTable({
    "bServerSide": true,
    "sAjaxSource": "/someapp/pagename",
    "sServerMethod": "POST",
    "fnServerParams": function ( aoData ) {
    aoData.push(
    {"name": "myX1name", "value": myX1},
    {"name":"myX2name", "value": myX2}
    );
    }
    });
    }else{
    oTable.fnReloadAjax(oTable.oSettings, supplier, val);
    }
This discussion has been closed.