我正在使用Angular 1 / Ionic 1 / PouchDB开发单页应用程序。
在主页上,我想显示一些合成信息,这些信息来自对大量数据的计算,并且可能需要几秒钟(我需要通过查询承诺查询PouchDB数据库,然后执行一些操作)计算)。
因此,我不想阻止主页显示,并立即显示,没有这种合成。然后,一旦后台工作完成,我想填充主页的相应<div>
。
我的问题是如何做到这一点......
我尝试了各种方法:
UI-Router中的resolve
无效,因为它会阻止主页在计算所有内容之前显示,这正是我想要避免的内容
在表单中显示$scope.syntheticData
变量(开头为空),并在计算完成后将此变量设置为计算值。但主页未更新。即使使用$scope.$apply()
。
在计算完成时使用$rootScope.$broadcast
触发事件。我使用$scope.$on
从主页控制器收听此事件。我收到了该事件,然后将$scope.syntheticData
设置为收到的值,但它仍然不起作用。即使使用$scope.$apply
。
我觉得这是非常基本的东西,但我找不到解决方法。非常感谢你的帮助!
回答Harshil Shah的评论,这里是控制器中我的代码的一个版本来更新范围:
// ctrl function
$scope.syntheticData = {};
$scope.$on('updateSynthetic', function() {
$scope.syntheticData = {}; // trial to make sure Angular sees a change on next line...
$scope.syntheticData.info1 = synthesis.data.info1;
$scope.$apply();
});
synthesis
是一个服务,通过PouchDB查询检索数据库数据,承诺进行计算then()
,并将结果存储到synthesis.data.info1
(以及info2, info3,...)
如果我在$ on事件回调中放入一个console.log,它会出现,所以当从服务中触发事件时会调用它。
答案 0 :(得分:0)
让函数最初返回一个空对象,然后在异步操作完成时填充该对象:
function expensiveData(params) {
var emptyObject = {};
emptyObject.$resolved = false;
var derivedPromise = asynchronousAPI(params).then(function(data) {
//Do computation here
//..
//Populatate emptyObject
angular.copy(data, emptyObject);
emptyObject.$resolved = true;
//return data for chaining
return data;
});
emptyObject.$promise = $q.when(derivedPromise);
return emptyObject;
});
如果派生的promise来自AngularJS框架之外,$q.when
将确保执行AngularJS摘要周期。如果没有,没有伤害。
然后在客户端代码中:
$scope.syntheticData = expensiveData(params);
syntheticData.$promise.then(function(data) {
//DO more stuff here
});
HTML
<div>{{syntheticData}}</div>
在每个AngularJS摘要周期中,插值{{ }}
创建的观察者将检查syntheticData
的值,并在DOM可用时将其放在DOM上。