Is there a way to void a delayed input event?

After reading this How to delay the .keyup() handler until the user stops typing? post, we have grasped how to implement delays. However, is there any suggestion on how to cancel a delayed event?

Take a look at this

In the scenario given, I want nothing to display after pressing the cancel button.

Yet, I am in need of a more versatile solution. One possibility could be to modify the delay() function in a way similar to this:

delay(fn, ms, cancelCallback)

Within this setup, the cancelCallback would serve as a method to terminate the delay. By cancelling the delay, we mean refraining from executing the fn() and simply doing nothing.

const inputElement = document.getElementById('input');
const buttonElement = document.getElementById('button');
const pElement = document.getElementById('p');

const delayInMs = 2000; // 2s delay

const delay = function (fn, ms) {
  let timer = 0;
  return function (...args) {
    clearTimeout(timer);
    timer = setTimeout(fn.bind(this, ...args), ms || 0);
  };
};

const print = text => pElement.innerHTML = text;

const handleKeyUp = e => print(e.target.value);

inputElement.addEventListener('keyup', delay(handleKeyUp, delayInMs));


// Introducing some new logic
const cancelDelay = () => {};

inputElement.addEventListener('click', cancelDelay);
<input id="input" />
<button id="button">Cancel</button>

<br />

<h6>You typed:</h6>
<p id="p"></p>

Answer №1

I managed to solve this issue independently and the solution seems quite straightforward.

const inputElement = document.getElementById('input');
const buttonElement = document.getElementById('button');
const pElement = document.getElementById('p');

const delayInMs = 2000; // Delay of 2 seconds

// Updated function for delaying execution
function delay(fn, ms) {
  let timer = 0;
    return {
      call(...args) {
        clearTimeout(timer);
        timer = setTimeout(fn.bind(this, ...args), ms || 0);
      },

      cancel() {
        clearTimeout(timer);
      },
    };
}

// Function to display text on the page
const print = text => pElement.innerHTML = text;

const myFunc = text => print(text);

const myFuncDelayed = delay(myFunc, delayInMs);

// Handling input keyups
const handleInputKeyUp = e => myFuncDelayed.call(e.target.value);
inputElement.addEventListener('keyup', handleInputKeyUp);


// Cancelling the delayed function
const handleBtnClick = () => { myFuncDelayed.cancel() };
buttonElement.addEventListener('click', handleBtnClick);
<input id="input" />
<button id="button">Cancel</button>

<br />

<h6>You typed:</h6>
<p id="p"></p>

Answer №2

In order to handle the cancel action for the specific element, it is important to set up a cancel handler specifically for the buttonElement rather than the inputElement. To track if the cancel button has been clicked, you can utilize a global variable flag that can be toggled to true when the cancel button is clicked and reset back to false within your input keyup event handler.

const inputElement = document.getElementById('input');
const buttonElement = document.getElementById('button');
const pElement = document.getElementById('p');

const delayInMs = 2000; // 2 second delay

let isCancelled = false;

const delay = function (fn, ms) {
  let timer = 0;
  return function (...args) {
    clearTimeout(timer);
    timer = setTimeout(fn.bind(this, ...args), ms || 0);
  };
};

const print = text => pElement.innerHTML = text;

const handleKeyUp = e => {
 if (!isCancelled) {
    print(e.target.value)
  }
  
  isCancelled = false;
};

inputElement.addEventListener('keyup', delay(handleKeyUp, delayInMs));


// Additional logic for cancel action
const cancelDelay = () => { isCancelled = true };

buttonElement.addEventListener('click', () => cancelDelay());
<input id="input" />
<button id="button">Cancel</button>

<br />

<h6>You typed:</h6>
<p id="p"></p>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Menu with hover functionality in JQuery that functions as a standard menu even when JavaScript is disabled in the browser

Is it possible to modify this code so that the hover point links' images do not appear if the browser has JavaScript disabled? And can the links function like a regular hover point even when JavaScript is disabled? <script type="text/javascript" s ...

Creating a Mobile-friendly Sidebar: A Guide to Angular 5

I've been seeing a lot of recommendations online about using Angular Material for creating a sidebar, but I'm hesitant to install an entire library just for one component. After following the instructions provided here, I managed to develop a si ...

Unforeseen box model quirks found in modern browsers when styling <table> elements

Here is a sample HTML document that demonstrates the issue: <!DOCTYPE html> <html lang="en"> <head> <meta http-equiv="X-UA-Compatible" content="IE=edge" /> <meta http-equiv="Content-Type" content="text/html; ...

Data sent through AJAX messaging is not being acknowledged

I recently made an AJAX request and set it up like this: $.ajax({ data : { id : 25 }, dataType : 'json', contentType : 'application/json; charset=utf-8', type : 'POST', // the rest of the ...

What steps do I need to take in order to ensure that when the word Hello is entered, the resulting output will display e:1, h:1, l:2, o:1

<!doctype HTML> <html> <body> <h3>Enter a string: </h3> <input id="myInput1" type="text"> <button onclick="count()">See output</button> //Click to see th ...

Acquire data from an HTML Element

I was provided with the following div that was already created for me: <div data-sudo-slider='{"slideCount":1, "moveCount":1, "customLink":"#slider-nav a", "continuous":true, "updateBefore":false, "effect":"sliceRevealDown", "auto":true, "speed":1 ...

Guide to adding new data to a JSON array

I'm currently working on implementing a punishment system using discord.js where the actions taken against users are logged by the Discord bot in a JSON file. The structure of the punishment data is as follows: { "username": "baduser# ...

Generating specific output based on the provided input parameter in JavaScript

I have encountered a problem where I am able to get the output, but I am struggling to figure out how to change certain elements. Specifically, I have the total salary but I am unsure how to modify the keys and achieve the desired format. The desired outp ...

Searching for partial nodes

I came across a helpful tutorial that explains how to perform a partial search. My goal is to have it so that when someone enters the text geor, it can locate a user named george. db.stores.find({storeName : {$regex : /Geor/}}).pretty() However, I am str ...

Efficiently Loading AJAX URLs using jQuery in Firefox

setInterval(function(){ if(current_url == ''){ window.location.hash = '#!/home'; current_url = window.location.hash.href; } else if(current_url !== window.location){ change_page(window.location.hash.split('#!/&apo ...

Updating Django database records with ajax

I'm currently working on a feature that involves filtering table data and updating the table using ajax. Here's what I have so far: Filter Form: <form id="search" method="POST" action="{% url 'article-filter' %}"> <input ...

What is the best way to place a button within a line of text

I am trying to achieve a layout similar to this: -------------------button------------------ I can add text inside the line, but it doesn't look good when I add a button. Any suggestions on how I can improve this? ...

A beginner's guide to handling multiple events with @click in Vue.js

In my project, I am developing a task manager application utilizing Vue.js, Vuetify, and Firebase. When the user clicks on "Add new note," a Vuetify dialog box pops up, prompting them to input data. Once they click save, the dialog box closes, and the inpu ...

Getting a 404 error when attempting to go straight to a URL in a Single Page Node App

Currently, my setup involves a NodeJS backend connected to a ReactJS frontend (without utilizing create-react-app). To bundle both the React frontend and the Node backend, I am using webpack. The webpack configuration generates an "dist" directory in the ...

What steps must be taken to display a div element upon clicking an object or entity within an Aframe scene?

Experiencing some coding issues that I could use help with. As a newcomer to Javascript, I might be making a beginner's error here. My goal is for the red tree on the globe in my example to trigger a red div box when clicked. Despite my efforts, I kee ...

Error Message in MUI Datagrid while Preprocessing Edit Cell Props

Is there a way to add an error message to the MUI preProcessEditCell function? I want to show "Supplier Name cannot be empty" as the error text. { field: "supplierName", headerName: "Name", width: 300, editable: tru ...

The Angular MatStepper is unable to detect saved values from two string arrays, although it is able to detect values from a different string array

In my application, there is a MatStepper component that facilitates navigation through the signup flow. A method exists to load cached values when available, causing the MatStepper to skip to Page 2. Subsequently, another method pre-fills the form with the ...

What is the reason behind generating auth.js:65 Uncaught (in promise) TypeError: Unable to access property 'data' of undefined?

Encountering a login issue in my Django application while using Axios and React-Redux. The problem arises when providing incorrect login credentials, resulting in the LOGIN_FAIL action. However, when providing the correct information, the LOGIN_SUCCESS act ...

Working with an array of object in Vuex for form handling

Looking to make updates to a vuex store that includes an array of objects: Users have a combobox for making selections, which then updates a property of the object in the database. However, every time I choose an item from the autocomplete (combobox) I e ...

What is the best way to ensure my jQuery plugin is up to date?

I have a question regarding the functionality of this plugin I am using. My goal is to update the timer it provides. To start the countdown timer with 5000 milliseconds remaining, I use the following code: $('#CountdownTimer').countdown({ remai ...