Reputation: 33
I've defined a search-input field in the navbar:
<input type="search" class="form-control" [formControl]="search" placeholder="search" aria-label="search">
In its controller I subscribe for changes and forward them to the search service:
this.search
.valueChanges
.subscribe(v => {
this.searchService.setSearchValue(v);
if (this.changeDetectorRef !== null && this.changeDetectorRef !== undefined &&
!(this.changeDetectorRef as ViewRef).destroyed) {
this.changeDetectorRef.detectChanges();
}
});
}
The search service holds the value and other components can request it.
searchValue: Subject<string>;
getSearchValue(): Observable<string> {
return this.searchValue;
}
setSearchValue(searchValue: string) {
this.searchValue.next(searchValue);
}
In my data view, I display all data filtered by the search-value:
<div *ngIf="(services | search:searchValue) as result">
<div *ngFor="let service of result">
{{ service.name }}
</div>
</div>
this.searchService.getSearchValue().subscribe(value => {
console.log("new search value: " + value);
this.searchValue = value;
});
The view doesn't update on the first keystroke however, and only updates itself after the second one.
I know that the correct search value arrives at the component as the console.log contains the expected value, but the view is nevertheless not updated. I've also tried changeDetectorRef.detectChanges()
and searchPipe.transform(this.services, value)
in my view but without success.
Could anyone tell me what went wrong? Thanks in advance.
Upvotes: 2
Views: 326
Reputation: 1191
Firstly. you don't have to use such a piece of code:
if (this.changeDetectorRef !== null && this.changeDetectorRef !== undefined &&
!(this.changeDetectorRef as ViewRef).destroyed) {
this.changeDetectorRef.detectChanges();
}
I suppose sometimes you catch an exception, that's why you don't unsubscribe from this.search.valueChanges
or you have logic that works very strange.
Try to use BehaviorSubject
instead of Subject
, difference being that Subject
don't store the last emitted value, whereas BehaviorSubjects
do.
Maybe one of your component or service initializes faster than other components, and your Subject
already fired value.
Upvotes: 1
Reputation: 1218
Assuming your doing the below code in ngonInit
this.searchService.getSearchValue().subscribe(value => {
console.log("new search value: " + value);
this.searchValue = value;
// Run the change detection here
this.changeDetectorRef.detectChanges();
});
Upvotes: 0