Как остановить запуск функции Jquery? - PullRequest
2 голосов
/ 12 июня 2019

Новичок здесь. Возможно, потому что я уже сонный и не могу найти решение. Я пытаюсь остановить функцию, когда нажимаю на другую кнопку. Вот код на данный момент:

Когда я нажимаю кнопку (.start), она запускает функцию, которая беспорядочно перемешивает текст без завершения. Но затем я хочу нажать на кнопку #stop и остановить запуск этой конкретной функции. Я пытался переключатели, protectDefault, event.stopPropagation (), setInterval и т. Д. Ни один из них не работает. Я пытался включить в свою функцию и снаружи.

Вот текущий код js:

$(".start").click(function(){
    var getTextNodesIn = function(el) {
    // Look at all the page elements and returns the text nodes
    return $(el)
      .find(":not(iframe,script)")
      .addBack()
      .contents()
      .filter(function() {
        return this.nodeType == 3; // Text node types are type 3
      });
  };

  // var textNodes = getTextNodesIn($("p, h1, h2, h3","*"));
  var textNodes = getTextNodesIn($("p"));

  function isLetter(char) {
    return /^[\d]$/.test(char);
  }

  var wordsInTextNodes = [];
  for (var i = 0; i < textNodes.length; i++) {
    var node = textNodes[i];

    var words = [];

    var re = /\w+/g;
    var match;
    while ((match = re.exec(node.nodeValue)) != null) {
      var word = match[0];
      var position = match.index;

      words.push({
        length: word.length,
        position: position
      });
    }

    wordsInTextNodes[i] = words;
  }

  function messUpWords() {
    for (var i = 0; i < textNodes.length; i++) {
      var node = textNodes[i];

      for (var j = 0; j < wordsInTextNodes[i].length; j++) {
        // Only change a tenth of the words each round.
        if (Math.random() > 1 / 10) {
          continue;
        }

        var wordMeta = wordsInTextNodes[i][j];

        var word = node.nodeValue.slice(
          wordMeta.position,
          wordMeta.position + wordMeta.length
        );
        var before = node.nodeValue.slice(0, wordMeta.position);
        var after = node.nodeValue.slice(wordMeta.position + wordMeta.length);

        node.nodeValue = before + messUpWord(word) + after;
      }
    }
  }

  function messUpWord(word) {
    if (word.length < 3) {
      return word;
    }

    return word[0] + messUpMessyPart(word.slice(1, -1)) + word[word.length - 1];
  }

  function messUpMessyPart(messyPart) {
    if (messyPart.length < 2) {
      return messyPart;
    }

    var a, b;
    while (!(a < b)) {
      a = getRandomInt(0, messyPart.length - 1);
      b = getRandomInt(0, messyPart.length - 1);
    }

    return (
      messyPart.slice(0, a) +
      messyPart[b] +
      messyPart.slice(a + 1, b) +
      messyPart[a] +
      messyPart.slice(b + 1)
    );
  }

  // From https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/random
  function getRandomInt(min, max) {
    return Math.floor(Math.random() * (max - min + 1) + min);
  }

  setInterval(messUpWords, 50);

});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="controls pt-5">
<button class="start">Simulate</button>
<button id="stop">Stop</button>
</div>
<br>
<br>
<br>
<div>
  <h1>Trying</h1>

  <p>Friends who have dyslexia described to me how they experience reading. She <em>can</em> read, but it takes a lot of concentration, and the letters seems to "jump around".</p>
</div>

Функция работает довольно хорошо. Мне просто трудно заставить другую кнопку остановить эту функцию ... Любая помощь будет принята, и я желаю вам хорошей недели.

Ответы [ 2 ]

4 голосов
/ 12 июня 2019

Вы не можете остановить выполнение функции, потому что только одна функция может выполняться одновременно в среде выполнения JavaScript (однопоточная). Когда вы нажимаете кнопку, чтобы попытаться остановить первую функцию, в действительности происходит то, что первая функция завершается, а затем запускается событие нажатия, связанное с кнопкой. И к тому времени первая функция завершена, поэтому уже слишком поздно ее останавливать.

Вы можете просмотреть асинхронные операции , которые выполняются вне среды выполнения JavaScript. В вашем случае, использование setInterval() для многократного запуска функции через равные промежутки времени, вероятно, будет лучшим способом. Это позволит вам проверять между вызовами, чтобы увидеть, произошло ли что-то еще, что должно остановить работу функции в следующий интервал.

Теперь вы используете интервальный таймер, но не настраиваете ссылку на него, поэтому вы не можете сказать, чтобы он остановился, когда вам это нужно. Решение состоит в том, чтобы связать переменную с таймером, а затем вызвать clearInterval() и передать ему ссылку на таймер, как показано здесь:

let timer = null; // This will hold a reference to the timer so you can stop it later

$("#stop").on("click", function(){
  clearInterval(timer); // Stop the timer
});

$(".start").click(function(){
   var getTextNodesIn = function(el) {
   // Look at all the page elements and returns the text nodes
   return $(el).find(":not(iframe,script)")
               .addBack()
               .contents()
               .filter(function() {
                  return this.nodeType == 3; // Text node types are type 3
                });
  };

  // var textNodes = getTextNodesIn($("p, h1, h2, h3","*"));
  var textNodes = getTextNodesIn($("p"));

  function isLetter(char) {
    return /^[\d]$/.test(char);
  }

  var wordsInTextNodes = [];
  for (var i = 0; i < textNodes.length; i++) {
    var node = textNodes[i];

    var words = [];

    var re = /\w+/g;
    var match;
    while ((match = re.exec(node.nodeValue)) != null) {
      var word = match[0];
      var position = match.index;

      words.push({
        length: word.length,
        position: position
      });
    }

    wordsInTextNodes[i] = words;
  }

  function messUpWords() {
    for (var i = 0; i < textNodes.length; i++) {
      var node = textNodes[i];

      for (var j = 0; j < wordsInTextNodes[i].length; j++) {
        // Only change a tenth of the words each round.
        if (Math.random() > 1 / 10) {
          continue;
        }

        var wordMeta = wordsInTextNodes[i][j];

        var word = node.nodeValue.slice(
          wordMeta.position,
          wordMeta.position + wordMeta.length
        );
        var before = node.nodeValue.slice(0, wordMeta.position);
        var after = node.nodeValue.slice(wordMeta.position + wordMeta.length);

        node.nodeValue = before + messUpWord(word) + after;
      }
    }
  }

  function messUpWord(word) {
    if (word.length < 3) {
      return word;
    }

    return word[0] + messUpMessyPart(word.slice(1, -1)) + word[word.length - 1];
  }

  function messUpMessyPart(messyPart) {
    if (messyPart.length < 2) {
      return messyPart;
    }

    var a, b;
    while (!(a < b)) {
      a = getRandomInt(0, messyPart.length - 1);
      b = getRandomInt(0, messyPart.length - 1);
    }

    return (
      messyPart.slice(0, a) +
      messyPart[b] +
      messyPart.slice(a + 1, b) +
      messyPart[a] +
      messyPart.slice(b + 1)
    );
  }

  // From https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/random
  function getRandomInt(min, max) {
    return Math.floor(Math.random() * (max - min + 1) + min);
  }

  timer = setInterval(messUpWords, 50); // Set interval reference to variable

});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="controls pt-5">
<button class="start">Simulate</button>
<button id="stop">Stop</button>
</div>
<br>
<br>
<br>
<div>
  <h1>Trying</h1>

  <p>Friends who have dyslexia described to me how they experience reading. She <em>can</em> read, but it takes a lot of concentration, and the letters seems to "jump around".</p>
</div>
0 голосов
/ 12 июня 2019

Вы можете проверить в верхней части функции messUpWords, чтобы увидеть, была ли нажата кнопка остановки.Если это так, вы можете очистить интервал, сбросить флаг кнопки остановки и выйти из процедуры.

var stopBtnClicked = false;
var stopBtn = document.getElementById("stop");
stopBtn.addEventListener("click", function() {
  stopBtnClicked = true;
}, false);

$(".start").click(function() {
  var getTextNodesIn = function(el) {
    // Look at all the page elements and returns the text nodes
    return $(el)
      .find(":not(iframe,script)")
      .addBack()
      .contents()
      .filter(function() {
        return this.nodeType == 3; // Text node types are type 3
      });
  };

  // var textNodes = getTextNodesIn($("p, h1, h2, h3","*"));
  var textNodes = getTextNodesIn($("p"));

  function isLetter(char) {
    return /^[\d]$/.test(char);
  }

  var wordsInTextNodes = [];
  for (var i = 0; i < textNodes.length; i++) {
    var node = textNodes[i];

    var words = [];

    var re = /\w+/g;
    var match;
    while ((match = re.exec(node.nodeValue)) != null) {    
      var word = match[0];
      var position = match.index;

      words.push({
        length: word.length,
        position: position
      });
    }

    wordsInTextNodes[i] = words;
  }

  function messUpWords() {
    if (stopBtnClicked) {
      clearInterval(jumbleTimer);
      stopBtnClicked = false;
      return;
    }  
  
    for (var i = 0; i < textNodes.length; i++) {
      var node = textNodes[i];

      for (var j = 0; j < wordsInTextNodes[i].length; j++) {
        // Only change a tenth of the words each round.
        if (Math.random() > 1 / 10) {
          continue;
        }

        var wordMeta = wordsInTextNodes[i][j];

        var word = node.nodeValue.slice(
          wordMeta.position,
          wordMeta.position + wordMeta.length
        );
        var before = node.nodeValue.slice(0, wordMeta.position);
        var after = node.nodeValue.slice(wordMeta.position + wordMeta.length);

        node.nodeValue = before + messUpWord(word) + after;
      }
    }
  }

  function messUpWord(word) {
    if (word.length < 3) {
      return word;
    }

    return word[0] + messUpMessyPart(word.slice(1, -1)) + word[word.length - 1];
  }

  function messUpMessyPart(messyPart) {
    if (messyPart.length < 2) {
      return messyPart;
    }

    var a, b;
    while (!(a < b)) {
      a = getRandomInt(0, messyPart.length - 1);
      b = getRandomInt(0, messyPart.length - 1);
    }

    return (
      messyPart.slice(0, a) +
      messyPart[b] +
      messyPart.slice(a + 1, b) +
      messyPart[a] +
      messyPart.slice(b + 1)
    );
  }

  // From https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Math/random
  function getRandomInt(min, max) {
    return Math.floor(Math.random() * (max - min + 1) + min);
  }

  var jumbleTimer = setInterval(messUpWords, 50);

});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

<div class="controls pt-5">
  <button class="start">Simulate</button>
  <button id="stop">Stop</button>
</div>
<br>
<br>
<br>
<div>
  <h1>Trying</h1>

  <p>Friends who have dyslexia described to me how they experience reading. She <em>can</em> read, but it takes a lot of concentration, and the letters seems to "jump around".</p>
</div>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...