我正在尝试使用所有预定义的手机类型创建会员的表单。
我正在为会员和电话类型提出两个api请求。这就是我的意思:
首先请求会员提供信息:
$scope.member = {
// $scope.member is returned from an api call
"name": "John Doe",
"phones": [{
"id": "Cell",
"phone": "(651) 111-1899",
"phone_unlisted": false
}, {
"id": "Work",
"phone": "(555) 121-1212",
"phone_unlisted": true
}]
};
获取手机类型的第二个请求:
myApp.controller("phoneTypes", function ($scope) {
// $scope.phoneTypes is returned from an api call
$scope.phoneNames = [{
"id": "Cell"
}, {
"id": "Cell 2"
}, {
"id": "Work"
}, {
"id": "Work 2"
}];
});
尝试创建此表单失败。
HTML -
<div ng-controller="memberInfo">
<h3>{{member.name}}</h3>
<form role="form" ng-controller="phoneTypes">
<h4>Phones</h4>
<div ng-repeat="phoneName in phoneNames" >
<label>{{phoneName.id}}</label>
//need to bind phone detail from $scope.member if exists otherwise leave blank
<input type="text" ng-model="member.phones.phone" />
unlisted: <input type="checkbox" ng-model="member.phones.phone_unlisted" />
</div>
</form>
</div>
我需要绑定每个匹配的手机类型的电话号码,否则请将输入字段留空。
我已经完成了各种教程和帖子,但我无法解决这个问题。我是AngularJS的新手,任何帮助都将不胜感激。
谢谢,
答案 0 :(得分:1)
一种可能的解决方案 - 虽然我觉得不舒服但最好将phones
数组重新映射到phones_object
,其中密钥是手机的id
。换句话说,在memberInfo
控制器的末尾,您可以:
$scope.member.phones_object = {};
$scope.member.phones.forEach( function( phone ) {
$scope.member.phones_object[ phone.id ] = phone;
} );
然后,在模板中,您使用该对象显示电话号码:
<div ng-repeat="phoneName in phoneNames" >
<label>{{phoneName.id}}</label>
<input type="text" ng-model="member.phones_object[ phoneName.id ].phone" />
unlisted: <input type="checkbox" ng-model="member.phones_object[ phoneName.id ].phone_unlisted" /> <br/>
</div>
这会给你我think is the result you want。
不幸的是,会破坏Angular的双向绑定,至少会破坏原始的$scope.members.phones
数据。如果需要,您可以使用$watch
来保持数据同步,或者在准备好向API重新提交数据时将其同步备份,具体取决于您的应用程序。
答案 1 :(得分:1)
另一种不会立即破坏双向绑定但又有其自身缺点的方法是直接将缺少的手机类型添加到$scope.member
。这是对现有代码的一个更大的修改。
首先,我们需要将控制器和模板组合到一个模板中:
<div ng-controller="memberInfo">
<h3>{{member.name}}</h3>
<form role="form">
<h4>Phones</h4>
<div ng-repeat="phone in member.phones" >
<label>{{phone.id}}</label>
<input type="text" ng-model="phone.phone" />
unlisted: <input type="checkbox" ng-model="phone.phone_unlisted" /> <br/>
</div>
</form>
</div>
请注意,我们现在repeat
直接通过member.phones
。但是没有所有可用的手机类型?正确,但我们现在就解决这个问题。
var myApp = angular.module("myApp", []);
myApp.controller("memberInfo", function ($scope) {
// $scope.member is returned from an api call
$scope.member = {
"name": "John Doe",
"phones": [{
"id": "Cell",
"phone": "(651) 111-1899",
"phone_unlisted": false
}, {
"id": "Work",
"phone": "(555) 121-1212",
"phone_unlisted": true
}]
};
var phoneNames = [{
"id": "Cell"
}, {
"id": "Cell 2"
}, {
"id": "Work"
}, {
"id": "Work 2"
}];
// make an array of the phone id's in $scope.member.phones
var currently_used_names = $scope.member.phones.map( function( phone ) {
return phone.id;
} ); // returns [ "Cell", "Work" ]
// add any phone names that weren't listed
phoneNames.forEach( function( name ) {
if ( currently_used_names.indexOf( name.id ) === -1 ) {
$scope.member.phones.push( {
"id": name.id,
"phone": "",
"phone_unlisted": false
} );
}
} );
});
在这种情况下,我们会向$scope.member.phones
添加任何需要使用某种默认模板列出的手机类型。
优势:保持双向绑定。
缺点:向$scope.member.phones
添加“错误”数据,但可能很容易根据需要手动过滤掉。
这是a fiddle来演示。