typescript Angular2 方法绑定错误:“检查后值已更改”
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/35710895/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Angular2 method binding error: "value has changed after it was checked"
提问by Claudiu
I am trying to make a circle board in Angular2. For the example I want to make 10 circles but in reality this number can change. I want to calculate the radius of each circle, so it would be dynamic and not static. See the picture for example
我正在尝试在 Angular2 中制作一个圆板。例如,我想制作 10 个圆圈,但实际上这个数字可以改变。我想计算每个圆的半径,所以它是动态的而不是静态的。例如看图片
This is my code
这是我的代码
@Component({
selector:"circle"
template: `
<svg>
<circle *ngFor='#item of forLength #i=index #l=last #e=even'
cx="50%" cy="50%" [style.r]="calculateRadius()" stroke="black" stroke-width="5" fill="white"></circle>
<svg/>
`
})
export class CircleComponent{
public maxRadius:number=25;
public totalRounds:number=10;
public x:number=30;
public calculateRadius():number{
var distanceBetweenCircles=this.maxRadius/(this.totalRounds-1);
this.x-= distanceBetweenCircles;
return this.x;
}
}
But I get the following error:
但我收到以下错误:
calculateRadius() in CircleComponent@7:30' has changed after it was checked.
Previous value: '-7.500000000000007'.
Current value: '-36.66666666666668' in [calculateRadius() in CircleComponent@7:30]
Is there maybe a better way of writing this for loop with *ngFor
instead of writing this in a separate method?
是否有更好的方法来编写 for 循环*ngFor
而不是在单独的方法中编写它?
回答by Mark Rajcok
In development mode (the default), change detection is run twiceto ensure that model changes have stabilized. This means that the ngFor
loop is evaluated twice. Hence property x
will continue to be decremented the second time change detection runs. Other activity in your app will also cause change detection to run, and x
will continue to be decremented. Therefore, you must write all view functions, like calculateRadius()
, assuming they will be executed many times. E.g.:
在开发模式(默认)下,更改检测运行两次以确保模型更改已稳定。这意味着ngFor
循环被评估两次。因此x
,第二次更改检测运行时,属性将继续递减。您应用中的其他活动也将导致运行更改检测,x
并将继续递减。因此,您必须编写所有视图函数,例如calculateRadius()
,假设它们将被执行多次。例如:
public calculateRadius(i):number{
return this.x - i*this.distanceBetweenCircles;
}
The Template Syntax dev guide mentions this when it describes idempotent expressions.
模板语法开发指南在描述幂等表达式时提到了这一点。
This will also solve the value has changed after it was checked
problem.
这也将解决value has changed after it was checked
问题。
You also need to bind SVG attribute r
using this syntax: [attr.r]="..."
, not [style.r]="..."
.
您还需要r
使用以下语法绑定 SVG 属性: [attr.r]="..."
,而不是[style.r]="..."
。
回答by basarat
“value has changed after it was checked”
“检查后值已更改”
The return from any value
must be deterministic. Means if I call value
(might be calculateRadius()
) with the sameinputs it should give the sameoutput.
any 的返回value
必须是确定性的。意味着如果我用相同的输入调用value
(可能是calculateRadius()
)它应该给出相同的输出。
So pass index
into calculateRadius
(or whatever value
is giving that error)
因此,通过index
进入calculateRadius
(或任何value
被赋予的错误)