我试图绑定一个视图的承诺。我不知道你是否可以直接做到这一点,但这是我试图做的。任何想法我做错了什么?
注意:源是有点设计的超时和使用静态数据,但这是为了使代码更容易诊断。
编辑:JSFiddle页面:http://jsfiddle.net/YQwaf/27/
编辑:解决方案:原来,你可以直接绑定承诺。我有我的原始代码的两个问题:
>使用setTimeout()而不是angular的$ timeout是一个问题。 Angular不知道它需要刷新UI超时时触发(你可以使用$ scope解决这个问题。$ apply在setTimeout,或者你可以使用$ timeout)
>绑定到返回promise的函数是一个问题。如果它第二次被调用,它做出另一个承诺。更好的是将范围变量设置为promise,并且只根据需要创建一个新的promise。 (在我的case,这是调用$ scope。$ watch在国家代码)
HTML:
<div ng:controller="addressValidationController"> Region Code <select ng:model="regionCode" ng:options="r.code as r.name for r in getRegions()"/> Country Code<select ng:model="countryCode"><option value="US">United States</option><option value="CA">Canada</option></select> </div>
JS:
function addressValidationController($scope,$q) { var regions = { US: [{code: 'WI',name: 'Wisconsin'},{code: 'MN',name: 'Minnesota'}],CA: [{code: 'ON',name: 'Ontario'}] }; $scope.getRegions = function () { var deferred = $q.defer(); setTimeout(function () { var countryRegions = regions[$scope.countryCode]; console.log(countryRegions); if(countryRegions === undefined) { deferred.resolve([]); } else { deferred.resolve(countryRegions); } },1000); return deferred.promise; }; }
WARNING: this answer was accurate when it was written,but as of 1.2 the Angular template engine does not handle promises transparently! — @Malvolio
是的模板引擎(和表达式)处理承诺透明,但我会分配promise到控制器中的scope属性,而不是每次调用一个函数返回一个新的promise(我认为这是你的问题,解决promise丢失,因为一个新的promise每次都返回)。
JSFiddle:http://jsfiddle.net/YQwaf/36/
HTML:
<div ng:controller="addressValidationController"> Region Code <select ng:model="regionCode" ng:options="r.code as r.name for r in regions"/> Country Code<select ng:model="countryCode"><option value="US">United States</option><option value="CA">Canada</option></select> </div>
JS:
function addressValidationController($scope,$q,$timeout) { var regions = { US: [{ code: 'WI',{ code: 'MN',CA: [{ code: 'ON',name: 'Ontario'}] }; function getRegions(countryCode) { console.log('getRegions: ' + countryCode); var deferred = $q.defer(); $timeout(function() { var countryRegions = regions[countryCode]; if (countryRegions === undefined) { console.log('resolve empty'); deferred.resolve([]); } else { console.log('resolve'); deferred.resolve(countryRegions); } },1000); return deferred.promise; }; $scope.regions = []; // Manage country changes: $scope.$watch('countryCode',function(countryCode) { if (angular.isDefined(countryCode)) { $scope.regions = getRegions(countryCode); } else { $scope.regions = []; } }); }