我有一个具有setTimeout的函数“ showElement”。如何使对“ btnSend”的eventListener中的函数的调用在另一个之后立即执行?
我尝试使用.then(),但没有用。
document.getElementById('btnSend').addEventListener('click', e => {
e.preventDefault();
result = validateInputs(email, subject, message);
if(result) {
showElement(document.getElementById('formGroupSpinner'), 2000);
showElement(document.getElementById('formGroupSuccessImg'), 2000);
resetForm();
}
});
//expects an html element and a number representing miliseconds. Shows the html element for that amount of time.
function showElement(element, mSeconds) {
element.classList.remove('d-none');
element.classList.add('d-block');
setTimeout( () => {
element.classList.remove('d-block');
element.classList.add('d-none');
}, mSeconds);
}
两个函数同时执行。
答案 0 :(得分:3)
有很多不同的方法,但是我建议使用这样的Promise:
document.getElementById('btnSend').addEventListener('click', e => {
e.preventDefault();
var result = validateInputs(email, subject, message);
if(result){
showElement(document.getElementById('formGroupSpinner'), 2000).then(()=>{
return showElement(document.getElementById('formGroupSuccessImg'), 2000);
}).then(()=>{
resetForm();
});
}
});
//expects an html element and a number representing miliseconds. Shows the html element for that amount of time.
function showElement(element, mSeconds) {
return new Promise((resolve, reject) => {
element.classList.remove('d-none');
element.classList.add('d-block');
setTimeout( () => {
element.classList.remove('d-block');
element.classList.add('d-none');
resolve();
}, mSeconds);
});
}
基本上,.then()
之后的函数仅在调用resolve();
后才执行。
或者,您也可以使用callback或async / await。
答案 1 :(得分:1)
函数结束后,您可以使用回调执行其他指令:
//First you add a param "callback" to the function
function showElement(element, mSeconds, callback) {
element.classList.remove('d-none');
element.classList.add('d-block');
setTimeout( () => {
element.classList.remove('d-block');
element.classList.add('d-none');
//Then you ask if the callback function is present and call it
if(callback && typeof callback === "function") callback();
}, mSeconds);
}
//Then use it in your event like this:
document.getElementById('btnSend').addEventListener('click', e => {
e.preventDefault();
result = validateInputs(email, subject, message);
if(result) {
showElement(document.getElementById('formGroupSpinner'), 2000, () => {
showElement(document.getElementById('formGroupSuccessImg'), 2000);
resetForm();
});
}
});
答案 2 :(得分:1)
您可以使用Promise
进行此操作。您必须将showElement()
函数包装到一个Promise中,并在setTimeout
触发后调用Promise解析程序。
然后,您的调用代码可以pipe
then
与showElement(document.getElementById('formGroupSpinner'), 2000).then(() => {
showElement(document.getElementById('formGroupSuccessImg'), 2000).then(() => {
resetForm();
});
});
一起使用您的诺言:
async
但是,这很快会导致回调地狱。
您可以使用async/await
来避免这种情况。
您将函数标记为await
,然后可以在其中使用await showElement(document.getElementById('formGroupSpinner'), 2000);
await showElement(document.getElementById('formGroupSuccessImg'), 2000);
resetForm();
来等待承诺解决,然后再继续下一个:
document.getElementById('btnSend').addEventListener('click', async e => {
e.preventDefault();
await showElement(document.getElementById('formGroupSpinner'), 2000);
await showElement(document.getElementById('formGroupSuccessImg'), 2000);
});
function showElement(element, mSeconds) {
return new Promise((resolve, reject) => {
element.classList.remove('d-none');
element.classList.add('d-block');
setTimeout(() => {
element.classList.remove('d-block');
element.classList.add('d-none');
resolve();
}, mSeconds);
});
}
这是一个工作示例:
.d-none {
display: none;
}
.d-block {
display: block;
}
<button id="btnSend">Send</button>
<div id="formGroupSpinner" class="d-none">Spinner</div>
<div id="formGroupSuccessImg" class="d-none">Success image</div>
all(test[, 2] >= cummax(test[, 2]))
答案 3 :(得分:0)
最简单的方法是将第二个 showElement 更改为 4000 ,而不是 2000 。
这样,一个将有2秒钟的超时,另外4秒钟。
答案 4 :(得分:0)
要做出承诺链,您首先必须有一个承诺。
function showElement(element, mSeconds) {
return new Promise(function(resolve,reject){
element.classList.remove('d-none');
element.classList.add('d-block');
setTimeout( () => {
element.classList.remove('d-block');
element.classList.add('d-none');
resolve();
}, mSeconds);
}
}
然后您可以使用showElement().then(/*something here */)