Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how do I debounce the @Output of an inner component?

I have a component that wraps another component <inner-component> and binds to the InnerComponent.innerChanged() custom event. I want to bubble up using an @output property, but I also want to debounce the output.

How do I use RxJS .debounce() or .debounceTime() to do this?

Something like this:

import {Component, Output, EventEmitter} from 'angular2/core'; import 'rxjs/add/operator/debounce'; import 'rxjs/add/operator/debounceTime';  @Component({   selector: 'debounced-component',   template: `     <div>       <h1>Debounced Outer Component</h1>       // export class InnerComponent{       //   @Output() innerChanged: new EventEmitter<string>();       //   onKeyUp(value){       //     this.innerChanged.emit(value);       //   }       // }       <input #inner type="text" (innerChange)="onInnerChange(inner.value)">     </div>   ` }) export class DebouncedComponent {   @Output() outerValueChanged: new EventEmitter<string>();    constructor() {}    onInnerChange(value) {     this.outerValuedChanged.emit(value); // I want to debounce() this.   } } 
like image 586
michael Avatar asked Oct 10 '16 13:10

michael


People also ask

What is the difference between @ input () and @ output () decorators?

@ Input () lets a parent component update data in the child component. Conversely, @ Output () lets the child send data to a parent component. The @ Input () decorator in a child component or directive signifies that the property can receive its value from its parent component. To use @ Input (), you must configure the parent and child.

What is the difference between @output () and @onchanges?

See the OnChanges section of the Lifecycle Hooks guide for more details and examples. The @ Output () decorator in a child component or directive lets data flow from the child to the parent. @ Output () marks a property in a child component as a doorway through which data can travel from the child to the parent.

How do I watch for changes on a component's input property?

To watch for changes on an @ Input () property, you can use OnChanges, one of Angular's lifecycle hooks. See the OnChanges section of the Lifecycle Hooks guide for more details and examples. Sending data to a parent component link The @ Output () decorator in a child component or directive allows data to flow from the child to the parent.

What is the difference between @input and @output?

@Input defines the input property in the component, which the parent component can set. The @output defines the output property (event), which we raise in the child component using the EventEmitter. The parent listens to these events.


1 Answers

To debounce values you could use a Subject. A subject is both an observable and a observer. This means you can treat it as an observable and pass values to it as well.

You could leverage this to pass the new values from the inner-component to it and debounce it this way.

export class DebouncedComponent {   @Output() outerValueChanged: new EventEmitter<string>();   const debouncer: Subject<string> = new Subject<string>();    constructor() {       // you listen to values here which are debounced       // on every value, you call the outer component       debouncer         .debounceTime(100)         .subscribe((value) => this.outerValuedChanged.emit(value));   }    onInnerChange(value) {     // send every value from the inner to the subject     debouncer.next(value);   } } 

This is untested pseudo-code. You can see a working example of the concept here (http://jsbin.com/bexiqeq/15/edit?js,console). It's without angular but the concept remains the same.


Update: For newer versions of Angular you might need a slight: change debouncer.debounceTime(100) gets changed to debouncer.pipe(debounceTime(100))

constructor() {       // you listen to values here which are debounced      // on every value, you call the outer component      debouncer        .pipe(debounceTime(100))        .subscribe((value) => this.outerValuedChanged.emit(value)); } 
like image 193
KwintenP Avatar answered Oct 14 '22 02:10

KwintenP