Jack Guy
Jack Guy

Reputation: 8523

Angular 2 RxJS check if mouse event is still active after delay

I'm using Angular 2 to make a directive. I have the following events bound to the host component:

host: {
    '(mouseenter)': 'onMouseEnter($event)',
    '(mouseleave)': 'onMouseLeave($event)'
}

I also created two streams and listeners on the directive to manage the two events

export class PopupDirective {
    private _mouseEnterStream: EventEmitter<any> = new EventEmitter();
    private _mouseLeaveStream: EventEmitter<any> = new EventEmitter();

    onMouseEnter($event) {
         this._mouseEnterStream.emit($event);
    }

    onMouseLeave($event) {
         this._mouseLeaveStream.emit($event);
    }
}

I want my subscribe to only be called if the mouseenter event is still active after a fixed delay (i.e., a mouseleave hasn't occured). I tried doing it this way, but it doesn't work (which makes sense, I just don't know how to fix it).

this._mouseEnterStream.flatMap((e) => {
  return Observable
    .of(e)
    .takeUntil(this._mouseLeaveStream);
}).delay(2000).subscribe(
  () => console.log('yay, it worked!')
);

Does anyone with Angular 2 / RxJS experience know how I should approach this?

Upvotes: 7

Views: 3771

Answers (2)

Thierry Templier
Thierry Templier

Reputation: 202156

The Günter's answer is exactly what you expect but you should use the of operator instead of the return one that doesn't exist.

this._mouseEnterStream.flatMap((e) => {
  console.log('_mouseEnterStream.flatMap');
  return Observable
      .of(e)
      .delay(2000)
      .takeUntil(this._mouseLeaveStream);
}).subscribe(
  (e) => {
    console.log('yay, it worked!');
    console.log(e);
  }
);

See the corresponding plunkr: https://plnkr.co/edit/vP3xRDXxFanqzLEKd3eo?p=preview.

Also, there is a proposal in Angular that aims to simplify the way observables are created from DOM events using Rx via template syntax.

Upvotes: 5

G&#252;nter Z&#246;chbauer
G&#252;nter Z&#246;chbauer

Reputation: 657238

Looks quite similar to How do I timeout an event in RxJS?

this.myStream = this._mouseEnterStream
    .flatMap((e) => {
        return Observable
            .of(e)
            .delay(2000)
            .takeUntil(mouseLeaveStream);
    });

myStream.subscribe((x) => { 
        console.log('onNext: ', x);
});

I don't use TS or Rx myself (only Dart) therefore I don't know if this is the correct syntax or if the name of the operators match with these available for Angular.

Upvotes: 3

Related Questions