我是GeoFire,FireBase和Angular的新手。我正在尝试创建一个函数,它将获取一些坐标并返回这些坐标附近的一些对象。
我从函数中返回一个promise,它赋予视图中使用的范围变量,希望当ready事件解析promise时,附近的对象数组将可用。
obj.findGroupsInViscinity = function(pos){
var gFire = factoryAuth.geoFire;
var fbaseRef = factoryAuth.usersRef;
var groupsInQuery = {};
var groupsInQueryAr = [];
var deferred = $q.defer();
var geoQuery = gFire.query({
center: [pos.coords.latitude, pos.coords.longitude],
radius: 2
})
geoQuery.on("key_entered", function(groupId, groupLocation, distance) {
console.log("--> key_entered 1");
groupsInQuery[groupId] = true;
// Look up the vehicle's data in the Transit Open Data Set
fbaseRef.child("groups").child(groupId).once("value", function(dataSnapshot) {
console.log("--> key_entered 2");
// Get the vehicle data from the Open Data Set
group = dataSnapshot.val();
// If the vehicle has not already exited this query in the time it took to look up its data in the Open Data
// Set, add it to the map
if (group !== null && groupsInQuery[groupId] === true) {
console.log("Adding group", group);
// Add the group to the list of groups in the query
groupsInQuery[groupId] = group;
groupsInQueryAr.push({"name": group.name});
}
})
}) // end ke_entered monitoring
geoQuery.on("ready", function() {
console.log("GeoQuery ready event received. groupsInQueryAr = ", groupsInQueryAr);
deferred.resolve(groupsInQueryAr);
geoQuery.cancel();
console.log("GeoQuery canceled");
}) // Cacnel the geoQuery once we have gotten all the groups in viscinity
return deferred.promise; // Return a promise that will be resolved when ready event fires
}
我注意到代码的key_entered部分连续两次调用,但在处理key_entered事件的代码完成之前,调用ready事件是因为所有key_entered事件都已触发。因此,虽然逻辑的key_entered部分构建了我希望传递的数组来解析promise,但是当我在ready事件中解析promise时它还没有准备好。
如何在处理完所有key_entered事件并正确构建我的对象数组后确保解析promise?
谢谢, 桑杰。
答案 0 :(得分:3)
我会说这有点an XY problem,我建议你只要把餐馆加载到你的视图中就可以了。在大多数情况下,这可能是更好的用户体验。
话虽如此,如果你想做你所要求的事情,你可以使用$.all()使其发挥作用。基本上,创建并返回您的延期承诺。从空列表开始,对于每个key_entered
事件,将新的承诺推送到列表中。然后,在您的ready
事件回调中,在承诺列表上执行$q.all()
,一旦完成(在承诺的then()
中),请执行deferred.resolve()
。< / p>