Weblurk
Weblurk

Reputation: 6802

In Angular2, how can I subscribe to a custom components event?

I have a component, which is a select drop down filled with offices:

@Component({
  selector: 'office-dropdown',
  template: `
    <select [(ngModel)]="selectedOffice" (ngModelChange)="handleChange()" class="form-control">
      <option value="0">Välj kontor</option>
      <option *ngFor="let office of offices$ | async" [ngValue]="office">
        {{office.officeName}}
      </option>
    </select>
    `
})
export class OfficeDropdownComponent implements OnInit {
  @Input() filters = {};
  @Output() myCustomOnChange = new EventEmitter();
  offices$: Observable<Office[]>;
  selectedOffice = 0;

  constructor(private apiService: ApiService) {}

  ngOnInit() {
    this.offices$ = this.apiService.doRequest()
      .map(response => response.offices);
  }

  handleChange() {
    this.myCustomOnChange.emit(this.selectedOffice);
  }
}

And In the following component I'm using that office dropdown, which works fine, but I want to connect an observable stream to its custom myCustomOnChange event and subscribe to it:

@Component({
  selector: 'admin-select-employee',
  template: `
      <office-dropdown #officeDropDown (myCustomOnChange)="handleOffice($event)"></office-dropdown>
  `
})
export class AdminSelectEmployeeComponent implements OnInit, OnDestroy, AfterViewInit {
  @ViewChild('officeDropDown') officeDropDown;
  officeDropDown$: Observable<any>;

  ngAfterViewInit() {
    this.officeDropDown$ = Observable
      .fromEvent(this.officeDropDown, 'myCustomOnChange');

    this.officeDropDown$.subscribe((event) => {
      console.log(event); // This never gets logged
    });
  }

  handleOffice(office){
     console.log(office); // This works
  }

But the console.log in the ngAfterViewInit never gets logged.

Any ideas why?

Edit I have stripped down a lot of the surrounding code to just illustrate where I am having issues and not bloat my example with unnecessary code. In actuality, the second component is filled with a lot more html/ts.

Upvotes: 2

Views: 1899

Answers (1)

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

Reputation: 657078

$event is only the emitted value, not the observable and @Output() doesn't fire DOM events what .fromEvent() is for.

I would just use

  officeDropDown$: Observable<any>;
  private officeDropDown = new Subject();

  constructor() {
    this.officeDropDown$ = this.officeDropDown.asObservable();
    this.officeDropDown$.subscribe((event) => {
      console.log(event); // This never gets logged
    });
  }

  handleOffice(office){
    console.log(office); // This works
    this.officeDropDown.next(office); 
  }

Upvotes: 2

Related Questions