javascript Angular2 ngModel 与 ngFor 变量
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/33346677/
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 ngModel against ngFor variables
提问by Langdon
Is it not possible (or not yet possible) to use ngModel
against values from ngFor
? Is Angular trying to protect me from bad performance?
是否不可能(或尚不可能)使用ngModel
来自 的值ngFor
?Angular 是否试图保护我免受不良性能的影响?
Works great: http://jsfiddle.net/langdonx/n5pjgev6/
效果很好:http: //jsfiddle.net/langdonx/n5pjgev6/
<input type="text" [(ng-model)]="value">{{value}}
Does not work so great: http://jsfiddle.net/langdonx/n5pjgev6/1
效果不太好:http: //jsfiddle.net/langdonx/n5pjgev6/1
<li *ng-for="#name of names">
<input type="text" [(ng-model)]="name">{{name}}
</li>
EXCEPTION: Cannot reassign a variable binding name
例外:无法重新分配变量绑定名称
I tried binding to the array as well, which... kind of works, but hiHymans focus and also throws an exception: http://jsfiddle.net/langdonx/n5pjgev6/2/
我也尝试绑定到数组,这......有点有效,但劫持焦点并抛出异常:http: //jsfiddle.net/langdonx/n5pjgev6/2/
<li *ng-for="#name of names; #i = index">
<input type="text" [(ng-model)]="names[i]">{{name}}
</li>
EXCEPTION: LifeCycle.tick is called recursively
例外:LifeCycle.tick 被递归调用
Edit:
编辑:
I can get around the LifeCycle.tick
issue using a more direct approach, but the focus is still stolen because ngFor
redraws things: http://jsfiddle.net/langdonx/n5pjgev6/3/
我可以LifeCycle.tick
使用更直接的方法解决这个问题,但由于ngFor
重绘内容,焦点仍然被盗:http: //jsfiddle.net/langdonx/n5pjgev6/3/
<li *ng-for="#name of names; #i = index">
<input type="text" [value]="names[i]" (input)="names[i] = $event.target.value">{{names[i]}}
</li>
采纳答案by bertrandg
I think ngFor
don't like tracking array elements which are primitive values having ngModel
on them.
我认为ngFor
不喜欢跟踪具有原始值的数组元素ngModel
。
If you remove the ngModel
inside the loop, it works.
如果您删除ngModel
循环内部,它会起作用。
It works too when I update jsfiddlewith :
当我使用以下内容更新 jsfiddle时它也有效:
this.names = [{name: 'John'}, {name: 'Joe'}, {name: 'Jeff'}, {name: 'Jorge'}];
and
和
<li *ng-for="#n of names"><input type="text" [(ng-model)]="n.name">{{n.name}}</li>
回答by andreim
A solution is to reference the value inside ngModel
by its index. Therefore [(ngModel)]="names[index]"
.
一种解决方案是ngModel
通过其索引引用内部的值。因此[(ngModel)]="names[index]"
。
But this is not sufficient because *ngFor
tracks items by value. As soon as the value is changed the old value cannot be tracked. So we need to change the tracking function to return an index, thus trackBy: trackByIndex
.
但这还不够,因为*ngFor
按价值跟踪项目。一旦更改了值,就无法跟踪旧值。所以我们需要改变跟踪函数来返回一个索引,因此trackBy: trackByIndex
.
This issue is explained here.
这个问题解释here。
Solution:
解决方案:
@Component({
selector: 'my-app',
template: `
<div>
<input type="text"
*ngFor="let name of names; let nameIndex = index; trackBy: trackByIndex"
[(ngModel)]="names[nameIndex]"/>
<br/>
{{ names | json }}
</div>
`,
})
export class App {
names: string[];
constructor() {
this.names = ['a', 'b', 'c'];
}
public trackByIndex(index: number, item) {
return index;
}
}