简体   繁体   English

修改ng-repeat中Angular Scope内的对象

[英]Modifying objects within Angular Scope inside ng-repeat

I'm creating a form in HTML using ng-repeat to generate the form elements from an object in the scope. 我正在使用ng-repeat在HTML中创建一个表单,以从作用域中的对象生成表单元素。 I also use that object to generate other elements outside of the ng-repeat. 我还使用该对象生成ng-repeat之外的其他元素。

A simplified example looks like this in HTML: HTML中的简化示例如下所示:

<div ng-app="App">
  <div ng-controller="Ctrl">
      <div class="block1">
          <form ng-repeat="(key, value) in test">
              <label>{{key}}</label>
              <input ng-model="value" />
              <p>{{value}}</p>
          </form>
      </div>
      <div class="block2">
        <p>
          {{test.a}}
        </p>
        <p>
            {{test.b}}
        </p>
      </div>
  </div>
</div>

and this in JS: 这在JS中:

angular.module('App', []);

function Ctrl($scope) {
    $scope.test = {
        a:"abc",
        b:"def"
    }
}

In this example, the text in block2 is set to the initial values of test.a and test.b . 在此示例中,block2中的文本设置为test.atest.b的初始值。 The input values and <p> values inside of the loop are also set to the initial value. 循环内的输入值和<p>值也设置为初始值。

When I modify the values within the inputs, the <p> values inside of the ng-repeat block update correctly, but the <p> tags in block2 fail to update. 当我修改输入中的值时,ng-repeat块内的<p>值会正确更新,但block2中的<p>标记无法更新。

Why is this the behavior? 为什么这是行为? Does ng-repeat create its own isolated scope? ng-repeat是否创建了自己的隔离范围? If so how can I get the controller level scope to update? 如果是这样,我如何才能让控制器级别范围更新? Also, could somebody explain the thinking behind this behavior and any advantages it provides? 此外,有人可以解释这种行为背后的想法及其提供的任何好处吗?

JSFiddle Showing the problem JSFiddle显示问题

ng-repeat creates a child scope for each repeated item. ng-repeat为每个重复项创建子范围。 As a result you are trying to pass a primitive to child scope which won't create a reference to parent. 因此,您尝试将原语传递给子范围,而不会创建对父级的引用。 When you pass objects however, you pass the original object reference. 但是,传递对象时,会传递原始对象引用。

From the mouth of one of the fathers of Angular: 从Angular的一位父亲口中说:

Always have a dot in ng-model 在ng-model中总是有一个点

This is a great video regarding Angular Best Practices given by Angular creator (2012/12/11). 这是 Angular创作者(2012/12/11)提供的关于Angular Best Practices的精彩视频 Go to minute 31 for well explained detail of this exact situation 转到第31分钟,详细了解这一情况

Modify data to array of objects: 将数据修改为对象数组:

$scope.test = [{ val:"abc",key:'a'}, {val:"def",key:'b'} ]

Then in repeater: 然后在转发器中:

<form ng-repeat="item in test">
  <label>{{item.key}}</label>
  <input ng-model="item.val" />
  <p>{{item.val}}</p>
</form>

DEMO DEMO

try this: 试试这个:

    angular.module('App', []);

function Ctrl($scope) {
    $scope.test = [
        {label:"a", value:"abc"},
        {label:"b", value:"def"}
    ]
}

and

<div ng-app="App">
  <div ng-controller="Ctrl">
      <div class="block1">
          <form ng-repeat="o in test">
              <label>{{o.label}}</label>
              <input ng-model="o.value" />
              <p>{{o.value}}</p>
          </form>
      </div>
      <div class="block2">
        <p>
          {{test[0].value}}
        </p>
        <p>
            {{test[1].value}}
        </p>
      </div>
  </div>
</div>

Angularjs uses the fact that objects are passed by reference. Angularjs使用对象通过引用传递的事实。 So, if you pass a object to a function and change the object inside the function, the object outside also changes. 因此,如果将对象传递给函数并更改函数内的对象,则外部对象也会更改。 Look at this updated JSFiddle 看看这个更新的JSFiddle

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM