使用OnPush策略时,子组件的视图不会被重新渲染
@Component({
selector: "parent",
template: `<child [userId]="(userId$ | async)"></child>`,
changeDetection: ChangeDetectionStrategy.OnPush
})
export class ParentCmp implements OnInit {
userId$: BehaviorSubject<string> = new BehaviorSubject<string>(null);
constructor(private activatedRoute: ActivatedRoute) { }
ngOnInit() {
this.activatedRoute.queryParams.subscribe(query => {
//notify child with BehaviorSubject
this.userId$.next(query["userid"])
}
}
}
@Component({
selector: "child",
template: `<div *ngIf="(userState$ | async) && userId">
{{(userState$ | async).user.id)}}
</div>`,
changeDetection: ChangeDetectionStrategy.OnPush
})
export class ChildCmp implements OnChanges {
@Input() userId: string;
private userState$: Observable<User>;
constructor(private store: Store<store.AppState>) { }
ngOnChanges(changes: SimpleChanges) {
//when it gets userId it starts to track fit user in ngrx store
this.userState$ = this.store
.select(state => state.user-list)
.map(userList => userList[this.userId])
.filter(user => !!user);
}
}
Child cmp从父级获取userId并且需要用户包含在ngrx store(userList)中,但是不会重新呈现子视图。当儿童的ChangeDetectionStrategy是默认值时,它完美地工作。这里有什么可能是错的? 角V2.4使用OnPush策略时,子组件的视图不会被重新渲染
如果您在ngOnChanges()
改变模型需要调用变化检测明确地
export class ChildCmp implements OnChanges {
@Input() userId: string;
private userState$: Observable<User>;
constructor(
private store: Store<store.AppState>,
private cdRef:ChangeDetectorRef
) { }
ngOnChanges(changes: SimpleChanges) {
//when it gets userId it starts to track fit user in ngrx store
this.userState$ = this.store
.select(state => state.user-list)
.map(userList => userList[this.userId])
.filter(user => !!user);
this.cdRef.detectChanges();
}
}
或可能会更好做userStates$
可观察到的,并保持相同的实例,而不是每次都创建一个新的ngOnChanges
被称为:
userId$: Subject<User> = new Subject<User>();
ngOnChanges(changes: SimpleChanges) {
//when it gets userId it starts to track fit user in ngrx store
this.store
.select(state => state.user-list)
.map(userList => userList[this.userId])
.filter(user => !!user)
.subscribe((user) => this.userId.next(user));
}
*小问题*'state.user-list'是否正确?我的意思不应该是'状态['user-list']' –
@PankajParkar我想问题是@Mergasov? –
@GünterZöchbauer感谢主题:当主体发出新的价值时,组件的视图被重新呈现。 – Mergasov
你可以创建plunker吗? – yurzui