使用 ajax 更新元素不影响直到 for 循环结束
Update element with ajax don't affect until for loop end
我想用 AJAX 一个接一个地打印很多数字。
像这样:(每一行都是前一行的更新!)
output is:
1
12
123
1234
12345
123456
...
我尝试了很多并阅读了很多相同的问题,但我找不到正确的答案。
真正的问题是 javascript 中的每个 FOR 循环在结束循环后都不会影响 DOM。我只想在处理较长的 运行 作业时更新 FOR 循环中的 DOM。
请看我的代码。
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
setTimeout(function() {
var counter = 100; // i want assign counter = 2000000000
for (var i = 0; i < counter; i++) {
document.getElementById("print_here").innerHTML += i;
}
document.getElementById("foo").innerHTML = "done!";
}, 50);
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
感谢您的回答和帮助解决这个问题。
您需要让调用堆栈完成,以便浏览器可以在页面上完成它的工作。如果您停滞在一个主线程中,页面更新将不会发生。
一种方法是使用 setImmediate 或 nextTick。这是非标准的,所以检查这个 polyfill:https://www.npmjs.com/package/browser-next-tick
基本上,您进行一次迭代,然后告诉浏览器尽快进行下一次迭代...这发生在新的调用堆栈上。
你的 DOM 是 "locked" 正在更新和重绘循环完成。您可以释放资源,让 DOM 更新每次将您的 DOM 更改包装在 setTimeout
中,类似于:
setTimeout(function(){
document.getElementById("print_here").innerHTML += i;
},1);
要确保 setTimeout
使用 i
的正确值,请使用 let i
而不是 var i
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
var counter = 3000; // i want assign counter = 2000000000
for (let i = 0; i < counter; i++) {
setTimeout(function() {
document.getElementById("print_here").innerHTML += i;
}, 1);
}
document.getElementById("foo").innerHTML = "done!";
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
I want change the #foo into "done!" after the FOR statement is END
您可以检查您是否在 setTimeout
中处理的最后一项,类似于:
if (i == counter - 1){
document.getElementById("foo").innerHTML = "done!";
}
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
var counter = 3000; // i want assign counter = 2000000000
for (let i = 0; i < counter; i++) {
setTimeout(function() {
document.getElementById("print_here").innerHTML += i;
if (i == counter - 1){
document.getElementById("foo").innerHTML = "done!";
}
}, 1);
}
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
这是适合您的工作代码:
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
setTimeout(function() {
var i, j, row = 5;
var html = "";
for (i = 1; i <= row; i++) {
for (j = 1; j <= i; j++) {
html += "<span>" + j + "</span>";
}
html += "</br>";
}
console.log(html);
document.getElementById("print_here").innerHTML = html;
}, 50);
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
Rows是你要打印的行数。
我想用 AJAX 一个接一个地打印很多数字。
像这样:(每一行都是前一行的更新!)
output is:
1
12
123
1234
12345
123456
...
我尝试了很多并阅读了很多相同的问题,但我找不到正确的答案。
真正的问题是 javascript 中的每个 FOR 循环在结束循环后都不会影响 DOM。我只想在处理较长的 运行 作业时更新 FOR 循环中的 DOM。
请看我的代码。
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
setTimeout(function() {
var counter = 100; // i want assign counter = 2000000000
for (var i = 0; i < counter; i++) {
document.getElementById("print_here").innerHTML += i;
}
document.getElementById("foo").innerHTML = "done!";
}, 50);
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
感谢您的回答和帮助解决这个问题。
您需要让调用堆栈完成,以便浏览器可以在页面上完成它的工作。如果您停滞在一个主线程中,页面更新将不会发生。
一种方法是使用 setImmediate 或 nextTick。这是非标准的,所以检查这个 polyfill:https://www.npmjs.com/package/browser-next-tick
基本上,您进行一次迭代,然后告诉浏览器尽快进行下一次迭代...这发生在新的调用堆栈上。
你的 DOM 是 "locked" 正在更新和重绘循环完成。您可以释放资源,让 DOM 更新每次将您的 DOM 更改包装在 setTimeout
中,类似于:
setTimeout(function(){
document.getElementById("print_here").innerHTML += i;
},1);
要确保 setTimeout
使用 i
的正确值,请使用 let i
而不是 var i
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
var counter = 3000; // i want assign counter = 2000000000
for (let i = 0; i < counter; i++) {
setTimeout(function() {
document.getElementById("print_here").innerHTML += i;
}, 1);
}
document.getElementById("foo").innerHTML = "done!";
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
I want change the #foo into "done!" after the FOR statement is END
您可以检查您是否在 setTimeout
中处理的最后一项,类似于:
if (i == counter - 1){
document.getElementById("foo").innerHTML = "done!";
}
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
var counter = 3000; // i want assign counter = 2000000000
for (let i = 0; i < counter; i++) {
setTimeout(function() {
document.getElementById("print_here").innerHTML += i;
if (i == counter - 1){
document.getElementById("foo").innerHTML = "done!";
}
}, 1);
}
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
这是适合您的工作代码:
$("#btn").on("click", dowork);
function dowork() {
document.getElementById("foo").innerHTML = "working";
setTimeout(function() {
var i, j, row = 5;
var html = "";
for (i = 1; i <= row; i++) {
for (j = 1; j <= i; j++) {
html += "<span>" + j + "</span>";
}
html += "</br>";
}
console.log(html);
document.getElementById("print_here").innerHTML = html;
}, 50);
}
#btn {
background: #1f1f1f;
padding: 10px;
font-weight: bolder;
color: #fff;
width: 50%;
margin: auto;
margin-top: 10px;
text-align: center;
cursor: pointer;
}
#print_here {
overflow-wrap: break-word;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="btn">CLICK TO DO WORK</div>
<div id="foo"></div>
<div id="print_here"></div>
Rows是你要打印的行数。