簡體   English   中英

在重新運行它之前,請等待使用settimeout的函數在javascript中完成

[英]Wait for function that makes use of settimeout to complete in javascript before rerunning it

請協助。

我需要wait操作完成才能在javascript中再次執行它。 這些操作可能在不同的時間運行。 並非一次全部。 我一次運行2個操作有一個問題,因為它們同時執行。

輸出應使用settimeout在“ textarea”中附加文本。 它需要等待完成,然后在調用“ arrayofrandomtext”數組的任意索引處開始鍵入下一個文本。 稍后仍然可以基於按鍵等調用“ ProcessText(someint)”。

  • 必須添加現有文本,而不是將其替換為0,而是添加即Hello World。 還有別的...

 var index=0; var arrayofrandomtext = ["Hello World","something else", "other stuff"]; function ProcessText(someint){ //These may run together next_letter(arrayofrandomtext[someint]); //wait to complete and rerun it with other text next_letter(arrayofrandomtext[someint]); //later on if the user hits a key this may run only next_letter(arrayofrandomtext[someint]); } function next_letter(text){ if (index <= text.length) { someControl.value = text.substr(0, index++); setTimeout(function () { next_letter(text); }, 50); } } 

嘗試創建文本值數組,使用Array.prototype.slice()創建文本值初始數組的副本; Array.prototype.shift()設置next_letter文本參數; 如果數組在對next_letter初始調用之后具有.length ,則遞歸調用ProcessText

 var arr = ["Hello...", "Some other text"], copy = arr.slice(), button = document.querySelector("input") someControl = document.querySelector("textarea"), index = 0; function ProcessText() { next_letter(copy.shift()) } function next_letter(text) { if (index <= text.length) { someControl.value = text.substr(0, index++); setTimeout(function() { next_letter(text); }, 50); } else { index = 0; if (!!copy.length) { ProcessText() } else { copy = arr.slice(); } } } button.onclick = ProcessText; 
 <input type="button" value="click" /><br /> <textarea></textarea> 

首先,您已經完成了此操作-但我想要一個工作版本進行演示。 您可以編寫一個遞歸函數,該函數在完成后對其自身調用settimeout。 例如,給定一個注銷字符串中每個字母的函數。

var log = function(text, index, duration) {
  console.log(text[index]);

  if (index < text.length - 1) {
    setTimeout(function() {
      log(text, index + 1, duration);
    }, duration);
  }
};

log("Hello There", 0, 1000);
log("Nice to see You", 0, 1000);

當然,現在,如果您運行此代碼,第二個日志功能將不會等待第一個。 您可以使用Promises和/或Callbacks執行異步控制流。 首先修改log函數以將回調作為參數。

var logCB = function(text, index, duration, cb) {
  console.log(text[index]);

  if (index < text.length - 1) {
    setTimeout(function() {
      logCB(text, index + 1, duration, cb);
    }, duration);
  } else {
    cb();  //execute callback
  }
};

現在,如果您傳遞了第二個函數(包裝在另一個函數中以延遲執行)。 作為您的第一個參數,它將在完成后執行。

var cb = function() {
  logCB("Nice to see you", 0, 1000);
};

logCB("Hello, World!", 0, 1000, cb);

雖然這可行,但對於多個嵌套來說卻變得笨拙。 更好的解決方案是使用promise-您只需要將logCB包裝到另一個函數中即可。 這里f是一個logCB。

var promiseLog = function(f, text, delay) {
  return new Promise(function(resolve, reject) {
     f(text, 0, delay, resolve);
  });
};

然后...我們可以將它們鏈接在一起,以..然后等待完成。

promiseLog(logCB, "Hello World", 1000)
 .then(function() {
   return promiseLog(logCB, "Hey There", 1000)
 });

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM