dalezak
February 6, 2017, 11:13pm
1
I’m running into an issue using [(ngModel)]
in a custom component with a RadioGroup
that has dynamic RadioButton
, getting the error:
Expression has changed after it was checked. Previous value: 'true'. Current value: 'false'.
If I remove the [(ngModel)]
binding, the RadioGroup
renders fine but no RadioButtons
are checked.
<ion-list radio-group [(ngModel)]="selection">
<ion-item *ngFor="let option of options">
<ion-label>{{option}}</ion-label>
<ion-radio [value]="option"></ion-radio>
</ion-item>
</ion-list>
I’m setting the options
and selection
in the ngOnInit
method of the component.
Any idea why this is happening?
I’m not sure you’ve given us enough information, because the following works for me:
fruits: string[];
selection: string;
ngOnInit(): void {
this.fruits = ["apple", "banana", "cherimoya"];
this.selection = "banana";
}
<ion-list radio-group [(ngModel)]="selection">
<ion-item *ngFor="let fruit of fruits">
<ion-label>{{fruit}}</ion-label>
<ion-radio [value]="fruit"></ion-radio>
</ion-item>
</ion-list>
1 Like
dalezak
February 6, 2017, 11:44pm
3
Hmm, still having the issue. The component does take a formGroup
and formControlName
as an input, something like:
<div [formGroup]="formGroup">
<ion-list radio-group [(ngModel)]="selection" [formControlName]="controlName">
<ion-item *ngFor="let option of options">
<ion-label>{{option}}</ion-label>
<ion-radio [value]="option" (ionSelect)="radioChanged($event)"></ion-radio>
</ion-item>
</ion-list>
</div>
Could the formGroup
or formControlName
be part of the problem?
Here is the full stacktrace from the error message:
[17:41:48] console.error: EXCEPTION: Error in ./ResponseAddPage class ResponseAddPage - inline template:34:78 caused
by: Expression has changed after it was checked. Previous value: 'true'. Current value: 'false'.
[17:41:48] console.error: ORIGINAL EXCEPTION: Expression has changed after it was checked. Previous value: 'true'.
Current value: 'false'.
[17:41:48] console.error: ORIGINAL STACKTRACE:
[17:41:48] console.error: BaseError@http://localhost:3000/build/main.js:13617:38
ExpressionChangedAfterItHasBeenCheckedError@http://localhost:3000/build/main.js:61791:20
checkBinding@http://localhost:3000/build/main.js:29926:115 checkHost detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
detectChangesInNestedViews@http://localhost:3000/build/main.js:117846:50 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
detectChangesInNestedViews@http://localhost:3000/build/main.js:117846:50 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
detectChangesInNestedViews@http://localhost:3000/build/main.js:117846:50 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
detectChangesInNestedViews@http://localhost:3000/build/main.js:117846:50 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
detectChangesInNestedViews@http://localhost:3000/build/main.js:117846:50 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48 detectChangesInternal
detectChanges@http://localhost:3000/build/main.js:117661:35
detectChanges@http://localhost:3000/build/main.js:117754:48
checkNoChanges@http://localhost:3000/build/main.js:62409:79 forEach@[native code]
tick@http://localhost:3000/build/main.js:41891:49 http://localhost:3000/build/main.js:41830:109
onInvoke@http://localhost:3000/build/main.js:44034:43 run@http://localhost:3000/build/polyfills.js:3:6487
next@http://localhost:3000/build/main.js:41830:84 http://localhost:3000/build/main.js:43234:56
__tryOrUnsub@http://localhost:3000/build/main.js:13398:20 next@http://localhost:3000/build/main.js:13347:34
_next@http://localhost:3000/build/main.js:13300:30 next@http://localhost:3000/build/main.js:13264:23
next@http://localhost:3000/build/main.js:21046:29 emit@http://localhost:3000/build/main.js:43226:80
checkStable@http://localhost:3000/build/main.js:44002:44
setHasMicrotask@http://localhost:3000/build/main.js:44073:25
onHasTask@http://localhost:3000/build/main.js:44046:46
_updateTaskCount@http://localhost:3000/build/polyfills.js:3:10535
invokeTask@http://localhost:3000/build/polyfills.js:3:9825
runTask@http://localhost:3000/build/polyfills.js:3:7093 i@http://localhost:3000/build/polyfills.js:3:3678
invoke@http://localhost:3000/build/polyfills.js:3:10877 dispatchEvent@[native code]
handleTapPolyfill@http://localhost:3000/build/main.js:78805:36
pointerEnd@http://localhost:3000/build/main.js:78715:35 [native code]
handleTouchEnd@http://localhost:3000/build/main.js:127568:41 [native code]
I still think you’re omitting the actual problem. Still working:
<div [formGroup]="form">
<ion-list radio-group [(ngModel)]="selection" formControlName="selection">
<ion-item *ngFor="let fruit of fruits">
<ion-label>{{fruit}}</ion-label>
<ion-radio [value]="fruit"></ion-radio>
</ion-item>
</ion-list>
</div>
ngOnInit(): void {
this.selection = "banana";
this.form = this._fb.group({
selection: ["banana"]
});
this.fruits = ["apple", "banana", "cherimoya"];
}
I don’t really understand why you have both an ngModel
binding and a bound control: I would just do one or the other, but even with both it doesn’t break for me.
1 Like
dalezak
February 7, 2017, 12:05am
5
Ah-ha! Trying to bind it in both the FormControl
and ngModel
must have been causing the issue, one was setting the checked
and the other one changing it.
In your last example, try changing the following.
this.selection = "banana";
this.form = this._fb.group({
selection: [""]
});
Curious if you get the same error I was experiencing?
Negative, Ghost Rider.
Still works fine that way. If I make selection
blank and set the control to “banana” instead, still no error, but now there is no checked selection at startup, so it looks like ngModel
trumps the form control if there’s a disagreement.
Any chance your error is being caused by the presence of some event handler (like ionChange
, for example)?
dalezak
February 7, 2017, 12:21am
7
Hmm, thats interesting, I thought maybe having conflicting values might be the issue.
Well the good news is, if I pass the value into the FormControl
when I’m building the FormGroup
, it properly binds to that value without needing to use ngModel
in the view.
I was previously only using FormControl
to include the Validators
, and not passing in an initial value.
Thanks for pointing this out, I’ll need to review my FormGroup
and FormControl
components, but this definitely helps me out!