Jquery:为每次迭代设置延迟
Jquery : Set delay for each iteration
假设这是我想要的逻辑:
// On fail return status = 500, else success will return PDF bytestream
function request() {
return $.ajax({
url: url,
async:false,
// other properties
});
}
$('#action').click(function(e) {
$("#loading").fadeIn("slow"); // display loading
while(true) {
if(request().status != 200) {
delay(3000);
} else { break; }
}
$("#loading").fadeOut("slow"); // hide loading
});
对于没有迭代和请求的测试延迟,此代码运行良好:
$(document).ready(function(){
$('#action').click(function(e) {
$("#loading").fadeIn("slow");
setTimeout(function() {
$("#loading").fadeOut("slow");
}, 5000);
e.preventDefault();
});
});
当我在里面放入一些循环和请求时,问题就开始了,比如:
var isOk;
$(document).ready(function(){
$('#action').click(function(e) {
$("#loading").fadeIn("slow");
while(true) {
request().always(function(jqXHR){
console.log(jqXHR);
if(jqXHR.status == 500) {
isOk = false;
setTimeout(function(){console.log("False")}, 3000);
} else { isOk = true; }
});
if(isOk) {break};
}
$("#loading").fadeOut("slow");
e.preventDefault();
});
});
这就像迭代之间没有延迟。加载符号fadeIn和fadeOut立即出现。知道如何对迭代进行正确的延迟吗?
使用promise(从技术上讲,本例中为jQuery Deferred,但概念相同(来修复流,省去了很多麻烦:
$('#action').click(function(e) {
$('#loading').fadeIn('slow'); // display loading
$.ajax(url).always(function (e) {
$('#loading').fadeOut('slow'); // hide loading
});
});
请注意,我正在使用.always()
。。。这样,即使出现错误,我们仍然会隐藏加载指示器。您可以为.fail()
添加另一个处理程序来捕获错误。
更好的是,使用.show()
和.hide()
,并使用CSS动画进行任何类似的渐变样式。虽然在这种情况下不太重要,但它使这些转换在浏览器引擎中得到了极大的优化,脱离了JavaScript,同时将应用程序逻辑与样式更加分离。
解析ajax请求时,应该调用.fadeOut((,如下所示:
$(document).ready(function(){
$('#action').click(function(e) {
e.preventDefault();
$("#loading").fadeIn("slow");
performRequest();
});
function performRequest() {
request()
.always(function(jqXHR){
console.log(jqXHR);
if(jqXHR.status === 500) {
console.log("False");
var t = setTimeout(function() {
performRequest(); // retry after 3sec.
clearTimeout(t);
}, 3000);
} else {
onRequestSuccess(); // success
}
});
}
function onRequestSuccess() {
$("#loading").fadeOut("slow");
}
});
以下是我所说的内容。在本例中,fadeOut是在fadeIn作为回调完成后执行的。我包括了一个暂停,以表明你也可以做到这一点。
$(function() {
$("#test").fadeIn(2000, function() {
setTimeout(function() {
$("#test").fadeOut(2000);
}, 1000);
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="test" style="display:none">
TEST DIV
</div>
如果您希望加载在每次ajax调用之前淡出,并在成功之后淡出,那么您需要在ajax成功回调中处理淡出。使用您的代码,这将在完成时淡出。
$(document).ready(function(){
$('#action').click(function(e) {
$("#loading").fadeIn("slow");
while(true) {
request().always(function(jqXHR){
console.log(jqXHR);
if(jqXHR.status == 500) {
setTimeout(function(){console.log("False")}, 3000);
} else {
$("#loading").fadeOut("slow");
break;
}
});
}
e.preventDefault();
});
});
由于ajax调用是asynchronous
,所以在执行下一行代码之前不会等待。
如果您想在完成时fadeOut,请在ajax调用的回调函数中或在该函数中运行fadeOut()
。
将以下内容放在您有//other properties
的位置:
complete: function(jqXHR, textStatus) {
$("#loading").fadeOut("slow");
}
否则必须使用delay()
、setTimeout()
。
延迟:
$("#loading").fadeIn(2000);
$("#loading").delay(2000).fadeOut(2000);
setTimeout:
$("#loading").fadeIn(2000);
setTimeout(function(){
$("#loading").fadeOut(2000);
}, 2000);
另一个建议是,处理Ajax调用中的错误,而不是while循环中的错误:
error: function(jqXHR, textStatus, errorThrown) {
setTimeout(function() {
request();
}, 3000);
}
另一个,接受@Brad的建议,使用CSS动画。
- 在es6中,将带有回调的事件侦听器设置为可迭代的
- 在JSON数组中进行迭代,并为其元素设置样式
- 如何根据DB中的值迭代选择并设置多个选项
- DOM:如何根据迭代器值设置元素宽度并在mouseover上调用函数
- ES6:在设置/映射迭代期间从集合/映射中删除元素是否危险
- Javascript使用for-in循环迭代器来设置变量
- JavaScript 上次迭代设置所有迭代的值
- 如何检索 java 设置并迭代来自 ajax 调用响应的值
- 如何在 for 循环中维护迭代变量的原始值,该循环设置事件调用,其中迭代值是函数的一部分
- 所有属性都设置为上次循环迭代值 [为什么?
- 通过对数组的迭代设置$scope属性值
- 在迭代器中设置inputText的id
- 如何迭代变量并动态设置其名称
- 如何设置class=“;活动的”;当使用迭代生成N个选项卡(引导程序)时
- 如何在迭代时将数组值设置为函数参数
- angularjs.for每次第二次迭代都无法设置对象属性
- 根据循环迭代设置变量名
- 在迭代时设置对象
- Jquery:为每次迭代设置延迟
- ECMAScript 6 Map &设置-安全在迭代期间删除