Identify when the user ceases typing in Angular 2

I am currently working on implementing a feature that detects whether the user is typing or not. I need to determine when the user has stopped typing for at least 3 seconds in order to perform certain actions. I have successfully detected when the user starts typing using the following code snippet:

     ngOnChanges(searchValue: string) {
    if (!this.searchChangeObserver) {
      Observable.create(observer => {
        this.searchChangeObserver = observer;
      }).debounceTime(3000) 
        .subscribe((data) => {
          if (data) {
            typingStuff();
          }
          else {
            notTypingStuff();
          }
        });
      this.searchChangeObserver.next(searchValue);
    }
  }
}

Now, I need to find a way to detect when the user stops typing so that I can execute the notTypingStuff() function.

Is there a simpler method to achieve this?

EDIT

In addition to the above code snippet, I am also utilizing the following code:

constructor(){
    this.modelChanged
      .debounceTime(300)
      .subscribe((data) => {
        if (data) {
          typingStuff();
        }
        else {
          notTypingStuff();
        }
      });
}

However, I still need to determine when the user stops typing for 3 seconds to trigger the notTypingStuff() function as well.

Answer №1

To avoid executing code while typing, you can set up an observable that triggers on input events with a debounce time:

HTML:

<input #yourElement [(ngModel)]="yourVar"/>

Component:

@ViewChild('yourElement') yourElement: ElementRef;

ngAfterViewInit() {
    Observable.fromEvent(this.yourElement.nativeElement, 'input')
        .map((event: Event) => (<HTMLInputElement>event.target).value)
        .debounceTime(3000)
        .distinctUntilChanged()
        .subscribe(data => notTypingStuff());
}

This setup ensures that the method is only called after 3000ms of inactivity following a modification in the input field, essentially when the user stops typing.

EDIT: Angular 9 w/ RxJS 6.5.4

ngAfterViewInit(): void {
    fromEvent(this.yourElement.nativeElement, 'input')
      .pipe(map((event: Event) => (event.target as HTMLInputElement).value))
      .pipe(debounceTime(3000))
      .pipe(distinctUntilChanged())
      .subscribe(data => notTypingStuff());
  }

Answer №2

Angular 6 is the version.

The HTML code snippet:

<input matInput type="text" (keyup)="searchInterest()" [(ngModel)]="keyword" [matAutocomplete]="auto">

This is the component:

public searchInterest() {
    let wordSearch = this.keyword;
    setTimeout(() => {
        if (wordSearch == this.keyword) {
            if (this.keyword) {
                //function that will return your list of objects
            }else{
                //implement code here
            }
        }
    }, 2000);
}

Answer №3

Whenever a user types in the element, I will capture the (keyup) event and verify if the time elapsed since the event was triggered is equal to or greater than 3 seconds.

Answer №4

I believe this approach could also be effective.

SCRIPT.ts

doSomething: any = null;
isActive: boolean = false;

trackActivity(event){

    this.isActive = true;

    clearTimeout(this.doSomething);

    this.doSomething = setTimeout( () => {
        this.isActive = false;
    }, 3000);

}

SCRIPT.HTML

<input (keyup)="trackActivity($event)">

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

In an Angular Material data table, table headers will always be displayed, even if there is no data

When utilizing the Angular material data table to present product-related information with sorting functionality using matSort, I faced an issue. Even when no data is available, the table headers still remained visible due to the [hidden]="!data" ...

Dealing with the issue of incompatible types in TypeScript with Vue 3 and Vuetify: How to handle numbers that are not assignable to type Readonly<any

Currently, I am utilizing Vite 3 along with Vue 3 and Vuetify 3 (including the Volar extension and ESLint). Additionally, I am incorporating the composition API in script setup mode. Within my HTML code, I am utilizing Vuetify's v-select. Unfortunate ...

I am experiencing difficulties with TypeORM connecting to my Postgres database

Currently, I am utilizing Express, Postgres, and TypeORM for a small-scale website development project. However, I am encountering challenges when it comes to establishing a connection between TypeORM and my Postgres database. index.ts ( async ()=>{ ...

An endless cascade of dots appears as the list items are being rendered

Struggling to display intricately nested list elements, Take a look at the JSON configuration below: listItems = { "text": "root", "children": [{ "text": "Level 1", "children": [{ "text": "Level 2", "children": [{ "text": ...

Would you like to learn how to display the value of a different component in this specific Angular 2 code and beyond

Hey there, I need your expertise to review this code and help me locate the issue causing variable "itemCount" to not display any value in about.component.html while everything works fine in home.component.html. I am attempting to only show "itemCount" in ...

How long do route providers typically last?

When using standalone components, we have the ability to place services into route providers. I couldn't locate this information in the documentation - what is the lifespan of these service instances? Are they destroyed when the route becomes inacti ...

Trouble configuring a React TypeScript router has arisen

Recently, I have successfully set up multiple routers in TypeScript. However, I am facing challenges in implementing the same in a new project for some unknown reason. import React from 'react'; import Container from './Components/Containers ...

Ensure that the key and value types in a Typescript Map are strictly specified

Is it feasible to generate a map that consists of key-value pairs, where the key is represented by a string and the value corresponds to an object containing specific properties defined by mapValue? type mapValue { first: string; second: boolean; } Yo ...

What is the proper syntax for Angular 2 form element attributes?

As I was browsing through this insightful article, I came across the following snippets: <input type="search" [formControl]="seachControl"> and <input type="text" formControlName="street"> This made me ponder on the correct syntax for ...

Troubleshooting d3js Type Errors in Angular (Updated Version)

Encountering numerous type errors with d3js when integrating it into Angular (typescript). svg.call(d3.zoom().on('zoom', () => { g.attr('transform', d3.events.transform); })); Error thrown: S2345: Argument of type 'Zo ...

Encountering issues when trying to build a Nestjs app with node-crc (rust cargo) in Docker

I am encountering an issue with building my Nest.js app using Docker due to a dependency called "node-crc" version "2.0.13" that fails during the docker build process. Here is my Dockerfile: FROM node:17.3.1-alpine RUN curl https://sh.rustup.rs -sSf | sh ...

Obtaining data from a cookie or service within the app-routing module

My angular site, www.domainname.com, utilizes an app-routing module with the following Routes: const routes: Routes = [ { path: "homepage/:lang/:country", ... }, ... { path: "**", redirectTo: "/homepage/en/gb", pathMatch: "fu ...

Tips for troubleshooting the error that occurs during the ng build --prod process

After creating an app, I attempted to build it using ng build --prod, only to encounter an error message related to the current version of Syncfusion. Below is the specific error I am experiencing: ERROR in ./node_modules/@syncfusion/ej2-angular-dropdown ...

Tips for saving the generated POST request ID for future use in another function

I am facing a challenge where I want to use the ID of a newly created Order as the OrderId for an OrderLine that needs to be created immediately after. After creating the Order, if I log the orderId INSIDE THE SUBSCRIBE METHOD, it shows the correct value. ...

Angular automatically protects routes by default

In the application I've created, there is a requirement for most routes to be protected and accessible only when logged in. Is it feasible to implement a default route guard while also specifying certain routes that should remain open? ...

What is the best way to exclude a particular subtype or property?

Is there a way to exclude a specific nested property? Let's take a look at an example. interface ILikes { article: string, page: string, userId: number | string, } interface IUserData { userName: string, isAdmin: boolean, ...data, ...

Error: Module not found '!raw-loader!@types/lodash/common/array.d.ts' or its type declarations are missing

I encountered a typescript error while building my NEXT JS application. The error message was: Type error: Cannot find module '!raw-loader!@types/lodash/common/array.d.ts' Below is the content of my tsConfig.json file: { "compilerOptions& ...

Reveal the class to the global scope in TypeScript

ClassExample.ts: export class ClassExample{ constructor(){} } index.html: <script src="ClassExample.js"></<script> // compiled to es5 <script> var classExample = new ClassExample(); //ClassExample is not defined < ...

Disappearing Ionic React useState value issue encountered when passing it as a prop parameter in a function

After transitioning from JavaScript to TypeScript, I encountered an issue with my useState hook not printing anything when used in a parent component. My confusion also extends to importing types in TypeScript. interface Props { sendTextMessage: (text? ...

Navigating to the tsconfig.json file based on the location of the file being linted

In my monorepo, each package currently contains a .eslintrc.cjs file with the following setup: Package-specific ESLint Configuration const path = require('path') const ts = require('typescript') const OFF = 0 const WARN = 1 const ERROR ...