问题
我有一个 PasswordComponent
,我想在其中使用 ng-template
。但是,我现在遇到 ExpressionChangedAfterItHasBeenCheckedError
错误m 编辑密码。我只想在 controlName === 'confirmPassword'
时使用 errorStateMatcher
并且我想不出另一种方法来有条件地绑定(bind) errorMatcher
完整代码可见here在 password.component.html
中,您会找到导致问题的 ng-template
:
<template *ngIf="controlName === 'confirmPassword'; then Custom else Default"></template>
<ng-template #Custom>
<input matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete" [errorStateMatcher]="errorMatcher"/>
</ng-template>
<ng-template #Default>
<input matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete"/>
</ng-template>
Note: Even if you remove the
ng-template
and put thengIf
on theinput
directly the error still shows. I originally thought the problem to be with theng-template
, but it's actually thengIf
.
错误
mat-error
数字各不相同,有时值为 aria-describedby: null
。
PasswordComponent.html:4 ERROR Error: ExpressionChangedAfterItHasBeenCheckedError: Expression has changed after it was checked. Previous value: 'aria-describedby: mat-error-3'. Current value: 'aria-describedby: mat-error-4'.
错误重现步骤
- 在密码字段中输入内容
- Tab/点击回到用户名
- Tab/点击返回密码
- 键入或删除字符,使
mat-error
消息发生变化 - 您将在控制台中看到
ExpressionChangedAfterItHasBeenCheckedError
。
最佳答案
尝试以下操作:
<input #Custom *ngIf="controlName === 'confirmPassword'; else Default" matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete" [errorStateMatcher]="errorMatcher"/>
<ng-template #Default>
<input matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete"/>
</ng-template>
编辑
简而言之,它可能归结为使用在呈现子项后已修改的父值的子模板。这通常发生在父级完成渲染之前渲染子级。我最初认为这是因为您将 errorStateMatcher 指令放在了子模板中。
看看下面的文章,它比我更好地解释了这个问题,并且还介绍了导致问题的一些常见模式以及如何更改它们以解决问题:
编辑
根据您的评论,可能是 ngIf 指令与 matInput 指令冲突。您可以尝试以下操作吗:
<ng-container *ngIf="controlName === 'confirmPassword'; else Default">
<input #Custom matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete" [errorStateMatcher]="errorMatcher"/>
</ng-container>
<ng-template #Default>
<input matInput [placeholder]="placeholder" [formControlName]="controlName" [type]="showPassword ? 'text' : 'password'" [autocomplete]="autocomplete"/>
</ng-template>
以下是一个工作示例:StackBlitz Example
关于javascript - 如何在不获取 ExpressionChangedAfterItHasBeenCheckedError 的情况下对子组件中的 Material 输入使用 ngIf,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54895316/