hese
hese

Reputation: 3417

javascript: how to show spinner until file downloads

I have a button to download an excel file. When the user clicks the button, the onClick function calls window.location= url

and when the downloading is done, the save as dialog popups with the file.

Now, I want to show a spinner until the file dialog appears. How do I do this?

I tried to create a spinner before "window.location" and hide it after that, but the spinner goes away immediately because window.location does not block until the file downloads.

Any ideas?

Thanks.

Upvotes: 8

Views: 26646

Answers (3)

Hawk
Hawk

Reputation: 561

This would be a solution which only works for Firefox browsers:

<script type="text/javascript">
//<![CDATA[
function download(url){
document.getElementById('spinner').style.display='';
frame = document.createElement("iframe");
frame.onload=function(){document.getElementById('spinner').style.display='none';}
frame.src=url;
document.body.appendChild(frame);
}
//]]>
</script>

In your HTML, have a spinner set up and ready to go:

<div id="spinner" style="background:url('/images/ico-loading.gif') #000 center no-repeat;opacity:.5;width:100%;height:100%;display:none;position:absolute" />

Then call it using this:

<button type="button" onclick="download('/spreadsheet.xls');">DOWNLOAD SPREADSHEET</button>

The button will call our javascript function with the URL we want to download. At this time we make the hidden spinner DIV visible and allow it take over the screen (note position absolute in style). An IFRAME is created to suck down the file. After the file downloads, it is given to the user and the .ONLOAD event is fired which hides the spinner DIV. All done with client side javascript!

Upvotes: 9

H.A.
H.A.

Reputation: 370

This code works for jQuery, but with simple modification also for javascript. With this you won't need to change your requests-codes at all.

  1. Create a div element which contains the animation (either another div element with css-animation or an animated gif in an img element) and give it the id = "loadingicondiv". For example like this

    <div id="loadingicondiv">
    <div id="loadingicon" style="background:url('imgs/logo.png') center no-repeat;opacity:1.0;display:none;position:absolute;z-index: 9999;"></div></div>

  1. Set the style of that div in your css file as follows


    #loadingicondiv{
        width: 100vw;
        height: 100vh;
        background: rgba(0,0,0, 0.3);
        position: fixed;
        z-index: 9999;
    }

  1. In the embeded js file enter this


    function showAnimation(){
        $('#loadingicondiv').css({display : ''});
    };

    function hideAnimation(){
        $('#loadingicondiv').css({display : 'none'});
    };

    $(document).ajaxStart(showAnimation).ajaxStop(hideAnimation);

This last line makes, that every request sent by your web application, executes the function "showAnimation" at the beginning and executes the function "hideAnimation", when the request is done.

If you don't use jQuery and need pure javascript, simply replace $('#loadingicondiv') with the following code

document.getElementById('loadingicondiv').style.display = 'none'

Note: In case you have some frequent updating on your website, which you don't want to show that animation for, just make the displaying of the animation dependent from a global variable, which you set to false before sending those special requests, which you don't want the animation to be shown for. And don't forget to set it to true, when the request is done by them.

Upvotes: 1

Guffa
Guffa

Reputation: 700690

You can't do that using just client script, because there is no event for when the download completes.

You would have to download the file through a proxy page on the server, with a unique identity in the URL so that each download could be identified. Then you could send AJAX requests from the script to the server to determine the status of the download.

Upvotes: 7

Related Questions