提问者:小点点

使用 ngRepeat 将输入绑定到基元数组 => 不可编辑的输入


这是我的问题的演示。

$scope.myNumbers = [10, 20, 30];

<div ng-repeat="num in myNumbers">
    <input type="text" ng-model="num">
    <div>current scope: {{num}}</div>
</div>

谁能向我解释为什么输入不可编辑/只读?如果是设计使然,背后的理由是什么?

更新2014年2月20日

看起来这不再是1.2.0版演示的问题了。但是请记住,尽管用户控件现在可以在较新的angularJS版本中编辑,但是修改的是子范围中的< code>num属性,而不是父范围。换句话说,修改用户控件中的值不会影响< code>myNumbers数组。


共3个答案

匿名用户

谁能向我解释为什么输入不可编辑/只读?如果是设计使然,背后的理由是什么?

从角度1.0.3开始,这是一种设计。Artem很好地解释了当你“直接绑定到每个ng-repeat项目”时1.0.3是如何工作的,也就是说,

<div ng-repeat="num in myNumbers">
  <input type="text" ng-model="num">

当您的页面最初呈现时,这是您的范围的图片(我删除了其中一个数组元素,因此图片的框会更少):

虚线显示了原型作用域继承
灰色线条显示子对象→ 父关系(即$parent引用的内容)
棕色线条显示$$nextSibling
灰色框是基本值。蓝色方框是阵列。紫色是物体。

注意,你在评论中提到的我的SO答案是在1.0.3发布之前写的。在1.0.3之前,当您在文本框中键入时,ngRepeat子作用域中的num值实际上会发生变化。(这些值在父作用域中不可见。)自1.0.3以来,ngRepeat现在在摘要周期中用父/MainCtrl作用域的myNumbers数组中的(未更改的)值替换ngRepeat-scopenum值。这基本上使输入不可编辑。

修复方法是在MainCtrl中使用一个对象数组:

$scope.myNumbers = [ {value: 10}, {value: 20} ];

然后绑定到ngRepeat中对象的< code>value属性:

<div ng-repeat="num in myNumbers">
  <input type="text" ng-model="num.value">
  <div>current scope: {{num.value}}</div>

匿名用户

这个问题现在由AngularJS的最新版本解决,该版本具有< code>track by功能,允许在原语上重复:

<div ng-repeat="num in myNumbers track by $index">
  <input type="text" ng-model="myNumbers[$index]">
</div>

页面不会在每次按键后重新绘制,这解决了焦点丢失的问题。AngularJS官方文档对此相当模糊和混乱。

匿名用户

似乎 Angular 无法写入以这种方式定义的模型。使用对初始$scope属性的引用,让它以正确的方式绑定值:

<div ng-repeat="num in myNumbers">
  <input type="text" ng-model="myNumbers[$index]">
</div>

相关问题