我正在编写一个简单的todo应用程序来学习Angular 2.我注意到使用管道会破坏更新行为。
我有以下模板
<input type="text" placeholder="Search" #queryBox (keyup)="query=queryBox.value">
<ul class="task-list">
<task-item *ng-for="#task of tasks | filter:containsString:query" [task]="task" (onDelete)="delete($event)"></task-item>
</ul>
当我点击删除按钮时,基础数据模型已更改,但此更改未反映在UI中。我已经确定这是因为过滤管道没有被调用。如果我将上面的行更改为
<task-item *ng-for="#task of tasks" [task]="task" (onDelete)="delete($event)"></task-item>
然后添加,删除之类的东西再次起作用,但很明显我没有过滤。为什么添加管道会破坏此绑定的更新行为?
答案 0 :(得分:3)
那是因为默认情况下管道是无状态(它们只渲染一次UI)。
你必须添加:
@Pipe({
selector: ...,
pure: false
})
当你设置纯粹的&#39;如果为false,Angular会在每个周期更新管道内的数据。
答案 1 :(得分:0)
默认情况下,管道是无状态/纯粹的。如果它们的输入没有改变,则在变化检测循环期间不执行管道。对于这个问题,我们在哪里
"#task of tasks | filter:containsString:query"
tasks
,containsString
和query
是输入,管道filter
是无状态/纯粹的。
tasks
是一个数组(参考)。
删除任务时,数组 reference 不会更改 - 管道的tasks
输入不会更改 - 因此不会执行无状态/纯管道。< / p>
如果我们使用pure: false
使管道有状态,那么管道将在每个更改检测周期进行评估 - 即使输入没有改变。
您可能还需要
onPush
更改检测策略(如果可能)或transform()
方法,使其返回相同的数组(引用)。详细解释了这些替代方案in this answer(我不想在此重复所有这些)。