更新javascript函数中的进度指示器
请参阅底部的更新 我已经研究了几十个问题,但都没能做到这一点 给出下面的代码,我如何强制它在每次迭代后更新我的简单进度指示器$log 编辑:我认为这个JSFIDLE说明了我的问题: 这是HTML:更新javascript函数中的进度指示器,javascript,progress,Javascript,Progress,请参阅底部的更新 我已经研究了几十个问题,但都没能做到这一点 给出下面的代码,我如何强制它在每次迭代后更新我的简单进度指示器$log 编辑:我认为这个JSFIDLE说明了我的问题: 这是HTML: <div id="test"></div> <div id="log"></div> 这就是函数 function createLevelMap() { var height = 300; var width = 1000; v
<div id="test"></div>
<div id="log"></div>
这就是函数
function createLevelMap() {
var height = 300;
var width = 1000;
var totalpixels = height * width; //used for calculating loading percentages;
var currentpixel = 0; //used for calculating loading percentages;
var x = 0;
var y = 0;
//lots of other variables
for (x = 0; x < width; x += 1) {
for (y = 0; y < height; y += 1) {
//lots of calculations with lots of variables
currentpixel += 1;
$("#log").html((currentpixel / totalpixels) * 100 + "%");
}
}
return ('done'); //actually returns a very long base64 encoded string
}
更新
我简化了它,因此我有一个单独的函数来渲染每一列,而不是整个网格。但是,使用setTimeout仍然不能正确显示进度
for (x = 0; x < width; x += 1) {
$("#log").html(((x + 1) / width) * 100 + "%<br>(sliver " + (x + 1) + "/" + width + ")");
setTimeout(createSliver(x), 100);
}
^^这将产生我期望的输出,但没有百分比更新。我把它改为setTimeoutfunction{createSliverx},100;按照评论中的建议,我甚至没有得到我的输出,但仍然没有增加百分比。这怎么样
var height = 300;
var width = 1000;
var totalpixels = height * width; //used for calculating loading percentages;
var currentpixel = 0; //used for calculating loading percentages;
incrementAndUpdate(currentpixel, totalpixels);
function incrementAndUpdate(currentValue, totalPixels) {
$("#log").html((currentValue / totalPixels) * 100 + "%");
if (currentValue < totalPixels) {
setTimeout(function () { incrementAndUpdate(currentValue + 1, totalPixels); }, 1);
}
}
这样做的工作量相同,但通过更少的setTimeout调用,速度更快。您可以调整调用setTimeout的频率,以便尽可能优化用户体验
下面是对您的提琴的更新:最好的解决方案是使用Web Workers。这使您可以在与UI更新完全不同的线程中运行处理。如果您需要支持没有web Worker的浏览器,则需要使用setTimeout为GUI更新提供运行机会 如果使用timeout方法,您将获得最佳体验,方法是设置一个max time,在中断循环并调用setTimeout之前让它运行。这将允许GUI重新绘制 例如:
您可以通过在somethingSlow方法中添加/删除零来加速/减慢它。因此,我通过从内部调用setTimeout函数来获得更新进度。这是我丢失的钥匙 以下是现在的基本格式:
function nextRow() {
x += 1;
setTimeout(function () { createSliver() }, 100);
if (x < width) { setTimeout(function () { nextRow() }, 100); }
}
function createSliver() {
//do stuff here
currentpixel += 1;
$("#log").html(((currentpixel) / totalpixels) * 100 + "%<br>(pixel " + (currentpixel) + "/" + totalpixels + ")");
y += 1;
if (y < height) {
setTimeout(function () { createSliver() }, 100);
} else {
y = 0;
}
function mainFunction() {
setTimeout(function () { nextRow() }, 100);
return (data);
}
但现在我的数据没有正常返回。我假设是因为现在所有的东西都是异步运行的。。。poop.这个更新$log吗?完成后,它显示100%我看到了你的原始代码,看起来你简化了它,但我假设totalpixels=宽度*高度?不用担心。在你的例子中,我也会初始化currentpixel,否则会出现pedantics。@BradChristie,是不是会出现pedantry?问题是每个工作函数都需要使用上一次迭代中的多个值。为什么会出现这个问题?将这些值传递到新函数调用中。这些文件中不会有超过一个同时运行,因此每个文件向下一个文件传递信息不会有问题。甚至使用闭包中的值,甚至使用全局可用的数据。
function incrementAndUpdate(currentValue, totalPixels) {
$("#log").html((currentValue / totalPixels) * 100 + "%");
// do a bit of work.
if (currentValue < totalPixels) {
var workFunction = function () { incrementAndUpdate(currentValue + 1, totalPixels); }
if (currentValue % 100 == 0)
setTimeout(workFunction, 1);
else
workFunction();
}
}
function nextRow() {
x += 1;
setTimeout(function () { createSliver() }, 100);
if (x < width) { setTimeout(function () { nextRow() }, 100); }
}
function createSliver() {
//do stuff here
currentpixel += 1;
$("#log").html(((currentpixel) / totalpixels) * 100 + "%<br>(pixel " + (currentpixel) + "/" + totalpixels + ")");
y += 1;
if (y < height) {
setTimeout(function () { createSliver() }, 100);
} else {
y = 0;
}
function mainFunction() {
setTimeout(function () { nextRow() }, 100);
return (data);
}