我什么时候知道GeoFire已经完成加载,因为它是基于事件的触发器 [英] When do I know GeoFire is finished loading as it is Event based trigger

查看:120
本文介绍了我什么时候知道GeoFire已经完成加载,因为它是基于事件的触发器的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以我使用GeoFire和AngularFire填充我的重复项目列表。有一个离子拉刷新清单。所以用户拉它,并得到当前更新的位置,并刷新列表(回想GeoFire重新填充列表)。
$ b

$ scope。 doRefresh = function(){if($ scope.doneLoading){$ scope.useCurrentLocation()。then(function(){$ scope.userCurrentLocation = {lat:geoLocation.getGeolocation()。lat,lng:geoLocation.getGeolocation .lng} angular.forEach($ scope.tasks,function(child){child。$ destroy();}); setupTaskListing(); $ scope。$ broadcast('scroll.refreshComplete');})}} function setupTaskListing (){console.log(setupTask is being called); if($ scope.tasks.length> 0){console.log(task is not empty!); $ scope.tasks = [];如果($ scope.query){console.log($ scope.query不为空:+ $ scope.query); $ scope.query.cancel(); } var radiusInMiles =($ scope.radius)* 1.60934; $ scope.query = taskService.setGeoQuery($ scope.userCurrentLocation.lat,$ scope.userCurrentLocation.lng,radiusInInformation); //我的服务来设置地理查询。 var geoQueryCallback = $ scope.query.on(key_entered,SEARCH:KEY_ENTERED);} $ scope。$ on(SEARCH:KEY_ENTERED,function(event,key,location,distance){// my service to (key);任务。$ loaded()。然后(函数(data){data.distance = parseInt(distance * 0.621371192))返回一个firebase对象,所以我使用$ loaded var task = taskService.getTask ; data.id = data。$ id; $ scope.tasks.push(data);});});



当你看到上面的代码,非常简单。 doRefresh()调用setupTaskListing()。它设置geoQueryCallback,当键入事件触发时,推入新的数据到$ scope.tasks数组。所以它的工作。然而,这个GeoFire结构的问题是...我不知道什么时候所有的任务完成进入半径...所以我不能建立一个加载程序和在半径内没有数据时提示。当没有数据输入时,key_entered事件永远不会触发,所以我永远不会知道是否有数据。它可以是NO数据或GeoFire仍在加载。如果我在$ scope。$ on中加载loader.hide()方法,实际上没有数据时它将永远不会触发。所以我的屏幕将永远加载。理想的用户体验应该停止加载,并提示用户增加搜索半径。如果我把$ .Open中的loader.hide()放在一个$ timeout的set $ timeout之外来调用它。在$ timeout运行之前,GeoFire需要更长时间才能加载数据。所以用户会提示变化半径屏幕然后闪回实际列表。再次糟糕的UX。那么...我的选择是什么? GeoFire中有什么可以使用的承诺吗?

解决方案

当出现以下情况时,Geofire将触发Query Ready事件:


所有当前数据已从服务器加载,所有初始事件已被触发。

请参阅 Geofire文档的这一部分

这里的代码示例:


  var onReadyRegistration = geoQuery.on(ready,function(){
console.log(GeoQuery已经加载并激发了所有其他事件的初始数据);
});



So I used GeoFire and AngularFire for populate my ng-repeat item lists. There is an ionic pull to refresh list. So user pull it and get the current updated location and refresh the list (recall the GeoFire to re-populate the list).

$scope.doRefresh = function() {
  if ($scope.doneLoading) {
    $scope.useCurrentLocation().then(function() {
      $scope.userCurrentLocation = {
        lat: geoLocation.getGeolocation().lat,
        lng: geoLocation.getGeolocation().lng
      }

      angular.forEach($scope.tasks, function(child) {
        child.$destroy();
      });

      setupTaskListing();

      $scope.$broadcast('scroll.refreshComplete');
    })
  }
}

function setupTaskListing() {
  console.log("setupTask is being called");
  if ($scope.tasks.length > 0) {
    console.log("task is not empty!");
    $scope.tasks = [];
  }
  if ($scope.query) {
    console.log("$scope.query is not empty:" + $scope.query);
    $scope.query.cancel();
  }
  var radiusInMiles = ($scope.radius) * 1.60934;
  $scope.query = taskService.setGeoQuery($scope.userCurrentLocation.lat, $scope.userCurrentLocation.lng, radiusInMiles); //My service to set Geo Query.
  var geoQueryCallback = $scope.query.on("key_entered", "SEARCH:KEY_ENTERED");
}

$scope.$on("SEARCH:KEY_ENTERED", function(event, key, location, distance) {

  //my service to get a single task. It return a firebase object. So I use $loaded
  var task = taskService.getTask(key);
  task.$loaded().then(function(data) {            
    data.distance = parseInt(distance * 0.621371192);
    data.id = data.$id;
    $scope.tasks.push(data);
  });
});

As you see the code above, pretty straight forward. doRefresh() call setupTaskListing(). And it setup geoQueryCallback that when key entered event fire, push new data into the $scope.tasks array. So it works.

But the problem for this GeoFire structure is...I have no idea when ALL the tasks finished entering the radius...So I can not set up a loader and prompt when there is NO data inside the radius. When there is NO data enter, the key_entered event never fire, so I will never know if there is data or not. It can be either NO data or GeoFire still loading. If I put the loader.hide() method inside $scope.$on, it will never fire when there is actually no data. So my screen will forever loading. The ideal UX should be stop loading and prompt people to increase the search radius. If I put the loader.hide() outside the $scope.$on with a set $timeout to call it. GeoFire take longer to load the data before $timeout run. So user will prompt the change radius screen then flash back to the actual list. Bad UX again. So...what is my option here? Is there some kind of promise I can use in GeoFire?

解决方案

Geofire fires a "Query Ready" event when:

All current data has been loaded from the server and all initial events have been fired.

See this section of the Geofire documentation.

The code sample from there:

var onReadyRegistration = geoQuery.on("ready", function() {
  console.log("GeoQuery has loaded and fired all other events for initial data");
});

这篇关于我什么时候知道GeoFire已经完成加载,因为它是基于事件的触发器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆