Looking for a way to improve performance when updating many cells often

Looking for a way to improve performance when updating many cells often

darrenmdarrenm Posts: 29Questions: 11Answers: 0

We're having a bit of an issue with a DataTables implementation on mobile devices. The table contains around 300 rows and each row has a cell containing a counter. The counter has to be updated every second so that it gives the appearance of a digital timer counting down seconds. Every cell has a different value.

To achieve this we are running a client-side script which loops through every row and updates the timer value. The issue is that this causes performance problems on mobile devices and the loop does not complete fast enough, so the timer values only appear to change every 4 or 5 seconds. (Note this worked fine in a previous iteration using standard HTML tables, which was just using JQuery to loop through every TR and update the cell contents).

In order to try and speed it up, we have used the following code to fetch only the visible rows and update the counter:

    var visiblerows = catalogueindextable.rows({ page: 'current' });
    visiblerows.every(function (rowIdx, tableLoop, rowLoop) {
        var newVar = countdownTimer(endtime[rowIdx + 1]);
        var targetcountdowncell = this.cell(rowIdx, "timeleft:name");
        targetcountdowncell.data(newVar);
    });

This has helped somewhat but it is still taking a few seconds to update the counter on the visible rows. By way of experiment, we tried turning deferRender on. This makes the counters on the first page work as desired, but it gets progressively slower as more pages are viewed, because this is obviously increasing the size of the array that DataTables has to search through when locating a specific row.

I think that this is the line that is causing the problem:

this.cell(rowIdx, "timeleft:name");

It seems to me that this API call is having to search through the entire dataset for rowIdx, which may be what is causing the slow update. Having to do that 10, 25, 50 times every second is killing the CPU on mobile devices.

What I was looking for was whether or not the 'visiblerows' variable in my code could give me a direct handle to the cell I want to update so that it doesn't have to search for it every time. Is that possible?

This question has an accepted answers - jump to answer

Answers

  • darrenmdarrenm Posts: 29Questions: 11Answers: 0

    Well interestingly I have done some profiling on this, and the code above, although a little slower on an iPad than a desktop, is still executing sub-second. By changing my code to this:

        setInterval(function () {
            UpdateCountdowns();
        }, 1000);
    
    function UpdateCountdowns() {
        alert("boop");
    }
    
    

    I have determined that the function is only firing every 4 or 5 seconds when deferRender = false but it fires every second if deferRender = true. So I guess there is something going on elsewhere in my code that is taking a long time when deferRender is off.

    I would still be interested in an answer to the above, if there is one, but I think I will have to look elsewhere for the performance issue.

  • kthorngrenkthorngren Posts: 20,275Questions: 26Answers: 4,765
    Answer ✓

    You can try something like the last example in the rows().every() docs. It doesn't use cell(). It simply gets the row data, updates the data then uses row().invalidate() to refresh the Datatables cache.

    I do agree its probably something else unless you have 300 rows being displayed on a page.

    Kevin

  • darrenmdarrenm Posts: 29Questions: 11Answers: 0

    Thanks, yes that's what I ended up doing and it works really well. I still had the problem but I traced it to another setInterval() task that was running every 5 seconds and doing a similar loop through all 300-odd rows! It was blocking the counter update task for a few seconds every 5 seconds, making the countdown slow to update. So once I fixed that too with the same approach, it's all good now.

This discussion has been closed.