【问题标题】:Why is change detection not happening here when [value] changed?当 [value] 更改时,为什么此处没有发生更改检测?
【发布时间】:2017-07-06 17:03:05
【问题描述】:

这是我的小伙伴:https://plnkr.co/edit/QPqciUngXeby2uECbokx?p=preview (您可能需要单击停止并运行几次才能正确加载)

表格没有变化。

但是当你服用

changeDetection: ChangeDetectionStrategy.OnPush

出来,桌子变了。

我的理解是,使用 OnPush,当 @Input 更改时,会触发更改检测。在这种情况下,@Input 是 [value],它链接到 this.testData。

为什么没有变化?

【问题讨论】:

    标签: angular


    【解决方案1】:

    因为onPush 更改检测会在输入发生更改或处理已侦听的事件时运行。

    如果您更改了this.testData,则需要运行更改检测以更新[value]="testData" 绑定。如果发生这种情况,将对<p-dataTable> 运行更改检测,因为它的输入已更改。

    App 上没有已更改的输入,因此无法检测到更改。

    您可以使用ChangeDetectorRef.markForCheck()标记App进行检查

    Plunker example

    【讨论】:

    • 因此,当 Root 使用 OnPush 时,Angular 似乎停止在子级别侦听 @Input 更改,对吗?当我使用[value]="testData$ | async"时,表会更新,异步管道是否会自动添加markForCheck?
    • 你的解释有点倒退。需要为App 组件运行更改检测,然后当它识别到更改时,它会更新模板中的绑定。当组件使用OnPush 时,setTimeout() 不会导致更改检测运行。这是<p-dataTable>@Input() 更新的时间。如果<p-dataTable> 使用OnPush,这将导致为<p-dataTable> 运行更改检测。是的,async 导致每次testData$ 发出事件时在<p-dataTable> 中运行更改检测。希望这会有所帮助。
    • 在你回答之前我原来的理解是,当App使用OnPush时,App下的任何组件都会继承OnPush策略。那是对的吗?而 [value] 是 中的 @Input(),对吗?所以在我原来的帖子中, 中的 @Input() 发生了变化,但表格没有刷新。因此,当 Angular 检测到父级别没有更改时,它似乎忽略了子级别的 @Input() 更改。我在这里使用一个简单的组件而不是 p-dataTable:plnkr.co/edit/xMu3km7XqvdT2pqCjRmi?p=preview
    • 不,OnPush 不会被孩子继承。角度变化检测从根组件运行到叶组件。如果有一个组件设置为OnPush,则更改检测将跳过此组件(包括其子组件)的检测。这并不意味着他们也在使用OnPush,但他们会受到使用OnPush 的父母的影响。 “而[value]<p-dataTable> 中的@Input(),对吧?”。这是正确的。 “所以在我原来的帖子中,<p-dataTable> 中的 @Input() 发生了变化,但表格没有刷新。”
    • 不,输入更改,因为未运行 App 的更改检测,因此 Angular 无法识别修改后的this.testData 需要传递给<p-dataTable>@Input()。这就是为什么什么都没有发生的原因。
    猜你喜欢
    • 2020-08-15
    • 2015-06-14
    • 2012-11-24
    • 2022-11-14
    • 1970-01-01
    • 2019-08-02
    • 1970-01-01
    • 1970-01-01
    • 2015-06-17
    相关资源
    最近更新 更多