Reputation: 996
I have a table of data that is being sorted alphabetically, and it's a rather large table. So the sorting takes a 2-3 seconds. The issue is, while that script is sorting the data the page locks up. So I would like to display a loading animation(or just loading text) during that time. Right now, my loading gif only appears AFTER the script is finished - despite me using setInterval or setTimeout. There must be something I'm missing. How can I display loading text or image BEFORE the script is run? Code is below:
$("#rotateArrowA").click(function() {
$(function() {
$("#loadingTwo").css("display","block");
$("#rotateArrowA").css("display","none");
$("#rotateArrowDownA").css("display","block");
setInterval(timeOut(), 1000);
});
function timeOut() {
var rows = $("#tableTwo tbody tr").get();
rows.sort(function(a, b) {
var A = $(a).children("td").eq(1).text().toUpperCase();
var B = $(b).children("td").eq(1).text().toUpperCase();
if(A > B) {
return -1;
}
if(A < B) {
return 1;
}
return 0;
});
$.each(rows, function(index, row) {
$("#tableTwo").children("tbody").replaceWith(rows);
$("#tableTwo tbody tr:odd").css("background-color", "#E6E6E6");
$("#tableTwo tbody tr:even").css("background-color", "white");
});
}
});
Also, I can't use any HTML 5 features for multi-threading... this has to work for legacy clients (IE 7-8).
Upvotes: 0
Views: 873
Reputation: 145172
If you're displaying enough data that sorting locks the browser for several seconds, you should really consider going with a virtual scrolling table instead. My favorite is SlickGrid.
Instead of just rendering out a giant table, you store your dataset in much more lightweight in-memory JS objects. (Which, consequently, can be sorted an order of a magnitude faster than the DOM-based sorting you're currently using.) SlickGrid only renders DOM elements for the portion of the table you are viewing, so there's much less strain on the browser.
You can also opt to load small chunks of your dataset at a time (the backend is implemented as simple pagination), giving you the ability to display effectively infinite rows in the browser with constant performance.
Upvotes: 1
Reputation: 192657
I'd recommend that you do the work in batches. This allows you to accomplish all the work, but not freeze the page.
There are patterns for doing this.
See this page, and the yeildingEach function.
In this case, I would overlay am "loading..." animation image in an absolutely-positioned DIV. .show()
the div before starting the sort, then .hide()
the div after it completes.
Upvotes: 0
Reputation: 183612
Change this:
setInterval(timeOut(), 1000);
(which means "call timeOut()
, and then call setInterval(...)
using the return-value of timeOut()
as the first argument") to this:
setTimeout(timeOut, 1000);
(which means "call setTimeout(...)
, passing the function timeOut
as the first argument").
Upvotes: 3