Scroll DataTable to Bottom

Scroll DataTable to Bottom

Taylor514ceTaylor514ce Posts: 74Questions: 8Answers: 0
edited January 2012 in General
I'm new to JQuery, forgive me for any obvious errors. I'm using JQuery UI, for tabs, and JQuery Datatables to load a log within a tab. The log contains HTML, table rows and data. The table:

[code]



StatusProcessTime  Message


Monitor Startupxx/xx/xxxx xx:xx am Placeholder value for monitor log.







Save the current log contents to a file, and start a new, empty log file.


[/code]

Note this is in a div for JQuery UI, and that the actual dynamic content is in the tbody.

The tbody is replaced with AJAX:

[code]

// jQuery Document
$(document).ready(function(){

$('#box-table-a').dataTable( {
"sDom": 'lfrt;' ,
"sScrollY": "510px",
"bScrollCollapse": false,
"bPaginate": false,
"bJqueryUI": true,
"bFilter": false,
"bAutoWidth": false,
"aoColumns": [null, null, null, { "sWidth": "80%" }]

} );

function loadLog(){
var oldscrollHeight = $("#statusbox").attr("scrollHeight") - 20;
$.ajax({
url: "/htmlFiles/log.html",
cache: false,
success: function(html){
$("#statusbox").html(html); //Insert log into the #statusbox div
var newscrollHeight = $("statusbox").attr("scrollHeight") - 20;
$("#statusbox").animate({ scrollTop: newscrollHeight }, 'normal');
},
});

}

setInterval (loadLog, 1500);

});

[/code]

This all works and looks great save for one issue: the table doesn't automatically scroll to the bottom. I had though the loadLog function would do this via the .animate method, but the newscrollHeight always contains NaN.

What am I doing wrong?

Thanks.

Replies

  • allanallan Posts: 63,540Questions: 1Answers: 10,476 Site admin
    > The tbody is replaced with AJAX:

    This will not work with DataTables. Any sorting / filtering etc would occur not he old data since you haven't told DataTables that there is new data for it to consider. You need to use the API if you want to replace the data in the table.

    Having said that, what is:

    [code]
    $("statusbox").attr("scrollHeight")
    [/code]

    If newscrollHeight is NaN, then I'm going to guess the scrollHeight attribute is null.

    Allan
  • Taylor514ceTaylor514ce Posts: 74Questions: 8Answers: 0
    Well, you're obviously right, because the scrolling / height isn't working. Simplifying my code somewhat for the AJAX section:
    [code]
    function loadLog(){
    $.ajax({
    url: "/htmlFiles/log.html",
    cache: false,
    success: function(html){
    $("#statusbox").html(html);
    },
    });

    }
    [/code]

    I get exactly the results I expect: on page load, the datatable renders. 1.5 seconds later, the tbody is replaced with the new content from the AJAX function, and the table looks perfect. New content, scrollbar, etc. The only issue I have is that it doesn't scroll to the bottom.

    I thought I needed to add a reference to the datatable within my loadlog() function and perform a scrollto(), but reading your reply tells me that my approach isn't compatible with datatables, and likely only works because I'm not using any pagination, TableTools, sorting, etc.

    Instead of replacing the table contents with jquery ajax, as I've done, I need to build the datatable from the start with an AJAX data source.

    If you can provide me with a link that describes how to create a datatable where the contents are loaded (and regularly reloaded) from a non-JSON datasource, I'd appreciate it.

    Thanks for the reply.
  • Taylor514ceTaylor514ce Posts: 74Questions: 8Answers: 0
    edited January 2012
    Ok, I've updated my code to use datatables with AJAX and a JSON data source. I've searched the forum and found the fnReloadAjax plugin, which I've added to my code.

    The HTML markup:
    [code]


    Status Monitor
    Job Launcher





    StatusProcessTime  Message









    <!-- TRIGGERS.HTML -->



    [/code]

    Followed by the script to create the fnReloadAjax() function, load the datatable, and set a timed reload:

    [code]
    $.fn.dataTableExt.oApi.fnReloadAjax = function ( oSettings, sNewSource, fnCallback, bStandingRedraw )
    {
    if ( typeof sNewSource != 'undefined' && sNewSource != null )
    {
    oSettings.sAjaxSource = sNewSource;
    }
    this.oApi._fnProcessingDisplay( oSettings, true );
    var that = this;
    var iStart = oSettings._iDisplayStart;

    oSettings.fnServerData( oSettings.sAjaxSource, [], function(json) {
    /* Clear the old information from the table */
    that.oApi._fnClearTable( oSettings );

    /* Got the data - add it to the table */
    var aData = (oSettings.sAjaxDataProp !== "") ?
    that.oApi._fnGetObjectDataFn( oSettings.sAjaxDataProp )( json ) : json;

    for ( var i=0 ; i
  • Taylor514ceTaylor514ce Posts: 74Questions: 8Answers: 0
    An update. I modified the fnReload Ajax function to store the current scrollTop() and set it after the table is drawn.

    [code]
    $.fn.dataTableExt.oApi.fnReloadAjax = function ( oSettings, sNewSource, fnCallback, bStandingRedraw )
    {
    if ( typeof sNewSource != 'undefined' && sNewSource != null )
    {
    oSettings.sAjaxSource = sNewSource;
    }
    this.oApi._fnProcessingDisplay( oSettings, true );
    var that = this;
    var iStart = oSettings._iDisplayStart;
    var scrollPos=$(".dataTables_scrollBody").scrollTop();

    oSettings.fnServerData( oSettings.sAjaxSource, [], function(json) {
    /* Clear the old information from the table */
    that.oApi._fnClearTable( oSettings );

    /* Got the data - add it to the table */
    var aData = (oSettings.sAjaxDataProp !== "") ?
    that.oApi._fnGetObjectDataFn( oSettings.sAjaxDataProp )( json ) : json;

    for ( var i=0 ; i
  • allanallan Posts: 63,540Questions: 1Answers: 10,476 Site admin
    Excellent stuff - thanks for posting your solution code. I'll look at integrating that into the fnReloadAjax plug-in offered on the site (possibly using the standing redraw parameter as a flag to optionally enable it when scrolling is enabled).

    Allan
This discussion has been closed.