首页 > 解决方案 > 在前台服务中获取当前位置

问题描述

我每 3 分钟运行一次前台服务。因此我的目标是:运行前台服务,获取当前用户位置,然后停止前台服务。所以现在我用这个:

locationCallback = object : LocationCallback(){
        override fun onLocationAvailability(locationAvailability: LocationAvailability?) {
            super.onLocationAvailability(locationAvailability)
            if(locationAvailability!!.isLocationAvailable){
                fusedLocationClient.lastLocation.addOnSuccessListener { location: Location? ->
                    if (location != null) {
                       // do my action with this location and finish the foreground service
                    }
                }
            }else{
                prepareFinishService() // finish service
            }
        }
    }
    fusedLocationClient.requestLocationUpdates(locationRequest,
            locationCallback, Looper.getMainLooper())

还有我的位置请求:

fun createLocationRequest(): LocationRequest {
    val locationRequest = LocationRequest.create()
    locationRequest.interval = 10000L * 10
    locationRequest.fastestInterval = 50000L
    locationRequest.smallestDisplacement = 10f
    locationRequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY
    return locationRequest
}

但在这个解决方案中,我得到的不是新鲜的位置。例如,用户更改位置但onLocationAvailability重新运行以前的位置。一段时间后,例如在我的服务运行 15 分钟后,它返回一个更新的位置。我知道我也可以添加这个回调:

override fun onLocationResult(locationResult: LocationResult?) {
     // my action with location
}

但根据文档: onLocationResult

“即使当 isLocationAvailable() 返回 true 时,onLocationResult(LocationResult) 可能并不总是被定期调用,但是设备位置是已知的,并且考虑到由活动的位置请求。”

可能不会调用此函数,并且我的服务将一直运行,直到下次启动。我不想要这种情况。是否有任何解决方案可以始终访问当前服务然后停止服务?

标签: javaandroidkotlingeolocation

解决方案


例如,用户更改位置,但 onLocationAvailability 重新运行以前的位置。

这就是这样getLastLocation做的。它返回最后一个已知位置,并不意味着最新位置。根据文档:

它特别适合不需要精确位置的应用 [...]

也就是说,为了获得不错的准确性,您应该使用requestLocationUpdates. 但不要手动启动/停止您的服务。如果您想定期更新用户位置,只需设置正确的参数即可。

LocationRequest locationRequest = new LocationRequest();
locationRequest.setInterval(1000*60*3); // max: 3 min
locationRequest.setFastestInterval(1000*60*1); // min: 1 min
locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);

推荐阅读