I am using Angular as the frontend
grid$: Observable < any[][] > | null = null
ngOnInit() {
this.grid$ = combineLatest([this.route.queryParams, source1, source2])
.pipe(
map(data => {
window.scroll(0,0) // go to top when route params change
//do something with the sources and route params
return grid;
})
)
}
I am using grid$
with async pipe
<ng-container *ngIf="grid$ | async as grid>
<div *ngFor="let column of columns>
<div *ngFor="let analyse of grid[column]"> ... </div>
</div>
</ng-container>
which is working fine.
Now I want to change the grid after specific events occured
changeGrid() {
// I also tried to just use map without assignment and return a new grid but then nothing happens
this.grid$ = this.grid$.pipe(
map(grid => {
// do something with grid
return grid;
})
}
}
which is also working. The only side effect I have is that combineLatest
is triggered as well although sources did not change so that you scroll automatically to the top again which is not intended. Could someone explain me why? I tried it with distinctUntilChanged
in combineLatest
but it is not triggered anymore when using changeGrid()
. I used distinctUntilChanged
in the following way
distinctUntilChanged((prev,curr) =>
{
return prev[0].get("id") != curr[0].get("id")
})
CodePudding user response:
First, by writing this.grid$ = ...
you lose the memory reference to its previous value. This means you can't stop the previous observable, which is in the combineLatest. This might be the cause of your issue.
Second, Since you use the queryParams observable, it means that on every query param change, your observable gets triggered. You didn't give enough code to show if it's the case, but this also might be the other cause of your issue.
Finally, distinctUntilChanged
compares memory references : when being used with combineLatest
, unless you provide a function to it, the operaor is useless (a new array is being created each time the combineLatest emits).