Iframe.readyState does not work in chrome
我即时创建了一个Iframe,并将下载二进制文件(xls,doc ...)的页面设置为url。 下载文件时,我会显示动画。 如果没有,我将其隐藏。
问题是Chrome不知道何时完全下载文件,即不完全加载iframe的时间。 我使用iframe属性
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | var iframe = document.createElement("iframe"); iframe.style.visibility ="hidden"; // I start a progress animation window.setTimeout(showProgressAnimation, 1000); // I start the file download iframe.src ='GetFile.aspx?file=' + fileName; document.body.appendChild(iframe); function showProgressAnimation() { if (iframe.readyState =="complete" || iframe.readyState =="interactive") { // I stop the animation and show the page animation.style.display = 'none'; progressBar.hide(); $('#page').show(); } else { // Chrome is always getting into this line window.setTimeout(showProgressAnimation, 1000); } } |
因此结果是无限循环。
我已经尝试了以下方法,但它在Firefox和Chrome中有效,但当内容为二进制文件时则无效:
1 2 3 4 5 6 7 8 9 10 11 | if ($.browser.mozilla || $.browser.webkit ) { iframe.onload = function showProgressAnimation() { animation.style.display = 'none'; progressBar.hide(); $('#page').show(); } } // IE else{ window.setTimeout(showProgressAnimation, 1000); } |
您可以使用
这是一个简单的例子
1 2 3 4 5 6 7 8 9 10 11 12 | var iframe = document.createElement("iframe"); iframe.style.display ="none"; // this function will called when the iframe loaded iframe.onload = function (){ iframe.style.display ="block"; alert("loaded"); }; // set the src last. iframe.src ='http://www.test.com'; // add it to the page. document.getElementById("one").appendChild(iframe); |
在这里测试:
http://jsfiddle.net/48MQW/5/
最后加载
http://jsfiddle.net/48MQW/24/
可下载文件的内容不会触发readystatechange事件处理程序或onload事件处理程序。 因此,您可以在服务器端一起设置cookie的文件内容,并由客户端定期检查此cookie。 例如:
服务器
1 2 3 | response.cookie('fileDownloaded','true'); response.header('attachment','your-file-name.any'); //...write bytes to response... |
客户
1 2 3 4 5 6 | var checker = setInterval(()=>{ if(document.cookie.indexOf('fileDownloaded')>-1){ alert('done'); clearInterval(checker); } },100); |
当然,您可以使用您的框架来正确检查cookie值,这只是poc,而不是安全的cookie解析器。
请尝试一下-您真的在一行到一行地混合dom和jQuery
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | var tId; function stopAnim() { // I stop the animation and show the page animation.hide(); progressBar.hide(); $('#page').show(); clearInterval(tId); } var iframe = $("<iframe />"); iframe.css("visibility","hidden"); iframe.on("readystatechange",function() { if (this.readyState =="complete" || this.readyState =="interactive") { stopAnim(); } }); iframe.on("load",function() { // can possibly be deleted if (tId) { stopAnim(); } }); iframe.attr("src","GetFile.aspx?file=" + fileName); $("body").append(iframe); tId = setInterval(function() { // update progress here }, 1000); // |
Sarkiroka的解决方案为我工作。 我在Cookie名称中添加了一个实例
1 2 3 4 5 | const instanceId ="some uuid retrieved from client"; response.cookie(`fileDownloaded-${instanceId}`,'true', { path: '/', secure: true, maxAge: 90000}); response.header('attachment','your-file-name.any'); //...write bytes to response... |
客户
1 2 3 4 5 6 | var checker = setInterval(()=>{ if(document.cookie.indexOf(`fileDownloaded-${instanceId}`)>-1){ alert('done'); clearInterval(checker); } },100); |