Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/465.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/209.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
下载一个小文件时,如何用Javascript显示进度条?_Javascript_Android_Ajax_Progress Bar - Fatal编程技术网

下载一个小文件时,如何用Javascript显示进度条?

下载一个小文件时,如何用Javascript显示进度条?,javascript,android,ajax,progress-bar,Javascript,Android,Ajax,Progress Bar,我编写了以下函数来处理Ajax请求以获取数据 var xhr = createCORSRequest('GET', url); if (!xhr) { alert('CORS not supported'); return; } xhr.onload = function() { var txt1 = xhr.responsetxt1; var heading = getheading(txt1); if (heading == 'PASS') {

我编写了以下函数来处理Ajax请求以获取数据

var xhr = createCORSRequest('GET', url);
if (!xhr) {
    alert('CORS not supported');
    return;
}
xhr.onload = function() {
    var txt1 = xhr.responsetxt1;
    var heading = getheading(txt1);

    if (heading == 'PASS') {
        var file = "My_URL" + ".js";
        downloadFile(file);
        //My code to display a progress bar here?
    } else {
        //Logic to handle failure to load
    }
};
这里是我的
下载文件
函数,用于下载文件。但是,我不明白如何:

  • 检查下载是否完成
  • 显示进度条以显示进度
如果你能描述一下它是如何工作的,那就太好了。谢谢

function downloadFile(fileName) {
    (function(d) {
        var ref = d.getElementsByTagName('script')[0];
        var js = d.createElement('script');
        js.src = fileName;
        ref.parentNode.insertBefore(js, ref);
        // My code to display a progress bar here?
    }(document));
}
好了,脚本元素没有进度事件。最好的方法是使用XHR获取脚本的主体,然后使用浏览器缓存进行第二次获取。问题是,您的脚本需要由浏览器解析,而且似乎没有相应的事件

我的解决方案是纯JS,因此您可以将其适应于您正在使用的任何框架。它假设实际下载时间约为总时间的70%,并将20%分配给浏览器。我使用awesome库的非精简版本作为更大的源文件

因为它在另一个沙箱中,进度调用是不准确的,但如果您提供自己的脚本,这应该不会是一个问题

请记住,这是一个相当精简的实现。例如,我使用一个简单的HR作为进度条

//这是我的示例文件的粗略大小估计
总_估计=1016*1024;
//我把人力资源作为一种资源
让bar=document.getElementById(“progressbar”);
let button=document.getElementById(“dlbtn”);
var js;//保存已创建的dom元素
var fileName;//保存我的被缓存的脚本地址
/*在(第一次)下载期间,此函数将被多次调用,其中包含有关加载了多少数据的信息*/
职能进展(e){
var percentComplete=e.已加载/总估算值;
if(如长度可计算){
完成百分比=e.加载/e.总计;
}
p=数学四舍五入(完成百分比*100);
log(“progress”,p+“%,”,e.loaded,“bytes loaded”)
bar.style=“width:”+(5+.6*p)+“%”;//我假设dl大约占总时间的60-70%
}
/*此函数在收到信息时调用。在初始下载结束时,readystate将为4,因此我们随后设置文件的src属性,触发重新下载,但利用浏览器的缓存。这并不理想,简单地“评估”数据可能会产生更好的结果。我只是假设您希望在页面上添加一个标记,并对其进行评估。*/
函数onReadyState(e){
设r=e.target;
//这几乎是逐字逐句地从http://vanilla-js.com/ ;)
if(r.readyState!=4 | | r.status!=200)
返回;
设l=r.responseText.length;
log(“Success!”,l,“字节总数”(+Math.round(l/1024)+“KB”);
bar.style=“宽度:70%”;
//只需添加/到下一行即可切换结束方法
/*您可以通过简单地评估返回的js()来加快进程。如是(请注意安全问题):
评估绑定(窗口)(r.responseText);
onScriptLoaded();
/*/
js.src=文件名;
bar.style=“宽度:80%”;
var ref=document.getElementsByTagName('script')[0];
ref.parentNode.insertBefore(js,ref);
//*/
};
//在对脚本求值时调用此函数:
函数onScriptLoaded(){
bar.style=“宽度:100%;背景色:浅绿色;”;
button.disabled=false;
log(“脚本已评估?”,三个?“是”:“否”);//演示文件将显示window.THREE
}
函数下载文件(文件){
button.disabled=true;
(职能(d){
//这有助于多次测试此脚本。不要保留它
fileName=file+“?bustCache=“+new Date().getTime();
log(“插入新脚本”);
js=d.createElement('script');
js.type=“text/javascript”;
js.defer=“defer”;
js.async=“async”;
var r=新的XMLHttpRequest();
bar.style=“width:5%”;//始终尽快作出反应
r、 addEventListener(“进度”,onProgress);
r、 打开(“获取”,文件名,true);
r、 onreadystatechange=onReadyState;
js.onload=onscriptload;
r、 send();
//我的代码在这里显示进度条?
}(文件);
}
#进度条{
高度:6px;
边界半径:3px;
宽度:0%;
边框颜色:绿色;
背景颜色:绿色;
}
下载
log(“虚拟脚本准备就绪”)


好吧,它更多地依赖于编程语言,而不是客户端。例如,PHP具有


至于客户端,Boris answer就是一个很好的例子!希望有帮助。

免责声明:我没有在
Android上测试这个。我只在
Chrome
(桌面)上测试过。您应该看到写入浏览器控制台的进度事件

var url = 'url/to/file/';
var request = new XMLHttpRequest();
request.responseType = "blob"; // Not sure if this is needed
request.open("POST", url);

var self = this;
request.onreadystatechange = function () {
    if (request.readyState === 4) {
        var file = $(self).data('file');            
        var anchor = document.createElement('a');
        anchor.download = file;
        anchor.href = window.URL.createObjectURL(request.response);
        anchor.click();            
    }
};

request.addEventListener("progress", function (e) {
    if(e.lengthComputable) {
        var completedPercentage = e.loaded / e.total;
        console.log("Completed: ", completedPercentage , "%");
    }
}, false);
request.send();

希望这有帮助。

您能添加一些描述吗?我无法理解。这是异步下载吗?如何进行同步下载(即等待下载完成)以加载文件?目前,在慢速网络中,文件下载速度较慢,但加载时间过长,并且e.LengthComputeable为FALSE(因为服务器上未设置内容长度头)。谢谢。是的,这是一个异步下载。同步下载时不能使用progressbar,因为它们是同步的,因此会阻止您的progressbar:)。要使进度准确,您需要文件大小。如果文件总是相同的,您可以使用我编辑的静态大小(就像我对TOTAL_ESTIMATE所做的那样)来添加注释和“更好”的评估方法。。。您可以通过复制我的代码片段并将行
/*更改为
/*您可以加速…
来尝试它。谢谢,快速提问,“脚本已评估”是什么意思?谢谢另外,eval.bind?我们正在加载javascript(用于我的demo Three.js)。加载后,我认为您希望运行该脚本;这是您的脚本中的两行代码
js.src=fileName
ref.parentNode.insertBefore(js,ref)。运行加载的脚本就是我的意思