Android:LocationManager vs谷歌Play服务
我想构建一个以获取用户当前位置为中心的应用程序,然后通过Google Places API查找用户附近的兴趣点(如酒吧、餐厅等) 在网上搜索开始的地方时,我遇到了一些使用Android:LocationManager vs谷歌Play服务,android,gps,geolocation,Android,Gps,Geolocation,我想构建一个以获取用户当前位置为中心的应用程序,然后通过Google Places API查找用户附近的兴趣点(如酒吧、餐厅等) 在网上搜索开始的地方时,我遇到了一些使用LocationManager类的教程,还有一些使用Google Play Services查找用户位置的教程 乍一看,他们都做同样的事情,但由于我是新手,我有点困惑,我不知道哪种方法最适合我的需要。所以,我想问你: 这两种查找位置的方法(如果有)有什么区别?您应该使用Google Play Services位置api而不是Lo
LocationManager
类的教程,还有一些使用Google Play Services查找用户位置的教程
乍一看,他们都做同样的事情,但由于我是新手,我有点困惑,我不知道哪种方法最适合我的需要。所以,我想问你:
这两种查找位置的方法(如果有)有什么区别?您应该使用Google Play Services位置api而不是LocationManager。根据文件: Google Play服务位置API优于Android 框架位置API(android.location)作为添加位置的一种方式 对你的应用程序的感知。如果您当前正在使用Android 框架位置API,强烈建议您切换到 谷歌播放服务位置API尽快 至于为什么要切换,谷歌表示: 谷歌定位服务API,谷歌Play服务的一部分, 提供了一个更强大的高级框架,可以自动 处理位置提供程序、用户移动和位置准确性。信息技术 还处理基于功耗的位置更新调度 您提供的参数。在大多数情况下,你会得到更好的电池 通过使用 位置服务API
Android上的用户位置 在Android上获取用户的位置比在iOS上要简单一些。首先,有两种完全不同的方法可以做到这一点。第一种是使用来自
Android.location.LocationListener
的Android API,第二种是使用Google Play Services APIcom.Google.Android.gms.location.LocationListener
。让我们把它们都看一遍
-此提供程序使用卫星确定位置。根据情况,此提供程序可能需要一段时间才能返回位置修复LocationManager.GPS\U提供程序
-该提供商根据基站和WiFi接入点的可用性确定位置。通过网络查找检索结果LocationManager.NETWORK\u提供商
-此提供程序将返回由其他提供程序生成的位置。当其他应用程序或服务请求位置更新时,您被动地接收位置更新,而不是自己实际请求位置LocationManager.PASSIVE\u提供程序
LocationManager
的对象,实现LocationListener
,并在LocationManager
上调用requestLocationUpdates
下面是一段代码片段:
LocationManager locationManager = (LocationManager) this.getSystemService(Context.LOCATION_SERVICE);
// Define a listener that responds to location updates
LocationListener locationListener = new LocationListener() {
public void onLocationChanged(Location location) {
// Called when a new location is found by the network location provider.
makeUseOfNewLocation(location);
}
public void onStatusChanged(String provider, int status, Bundle extras) {}
public void onProviderEnabled(String provider) {}
public void onProviderDisabled(String provider) {}
};
// Register the listener with the Location Manager to receive location updates
locationManager.requestLocationUpdates(LocationManager.NETWORK_PROVIDER, 0, 0, locationListener);
很好地解释了代码。但他们也提到,在大多数情况下,你会得到更好的电池性能,以及更适当的准确性,而不是使用。现在混乱开始了
GooglePlayServicesClient
。要连接到客户端,您的活动(或片段等)需要实现GooglePlayServicesClient.ConnectionCallbacks
和GooglePlayServicesClient.OnConnectionFailedListener
接口。
下面是一个示例代码:
public class MyActivity extends Activity implements ConnectionCallbacks, OnConnectionFailedListener {
LocationClient locationClient;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_my);
locationClient = new LocationClient(this, this, this);
}
@Override
public void onConnected(Bundle bundle) {
Location location = locationClient.getLastLocation() ;
Toast.makeText(this, "Connected to Google Play Services", Toast.LENGTH_SHORT).show();
}
@Override
public void onDisconnected() {
Toast.makeText(this, "Connected from Google Play Services.", Toast.LENGTH_SHORT).show();
}
@Override
public void onConnectionFailed(ConnectionResult connectionResult) {
// code to handle failed connection
// this code can be found here — http://developer.android.com/training/location/retrieve-current.html
}
- 为什么
locationClient.getLastLocation()为空
locationClient.getLastLocation()
从客户端获取最后一个已知位置。但是,如果至少有一个客户端连接到融合位置提供程序,则融合位置提供程序将仅维护后台位置。一旦第一个客户端连接,它将立即尝试获取位置。如果您的活动是第一个连接的客户端,并且您立即在onConnected()
中调用getLastLocation()
,则可能没有足够的时间让第一个位置进入。这将导致location
为null
要解决此问题,您必须(不确定地)等待提供者获取位置,然后调用getLastLocation()
,这是不可能知道的。另一个(更好的)选择是实现com.google.android.gms.location.LocationListener
接口,以接收定期的位置更新(并在获得第一次更新后将其关闭)
在这段代码中,您正在检查客户端是否已经拥有最后一个位置(在onConnected
)。如果没有,则请求位置更新,并在获得更新后立即关闭请求(在onLocationChanged()
callback中)
注意,locationClient.requestLocationUpdates(locationRequest,this)
必须位于onConnected
回调中,否则您将获得IllegalStateException
,因为您将尝试在未连接到Google Play Services客户端的情况下请求位置
public class MyActivity extends Activity implements ConnectionCallbacks, OnConnectionFailedListener, LocationListener { // . . . . . . . . more stuff here LocationRequest locationRequest; LocationClient locationClient; @Override protected void onCreate(Bundle savedInstanceState) { // . . . . other initialization code locationClient = new LocationClient(this, this, this); locationRequest = new LocationRequest(); // Use high accuracy locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY); // Set the update interval to 5 seconds locationRequest.setInterval(UPDATE_INTERVAL); // Set the fastest update interval to 1 second locationRequest.setFastestInterval(FASTEST_INTERVAL); } // . . . . . . . . other methods @Override public void onConnected(Bundle bundle) { Location location = locationClient.getLastLocation(); if (location == null) locationClient.requestLocationUpdates(locationRequest, this); else Toast.makeText(getActivity(), "Location: " + location.getLatitude() + ", " + location.getLongitude(), Toast.LENGTH_SHORT).show(); } // . . . . . . . . other methods @Override public void onLocationChanged(Location location) { locationClient.removeLocationUpdates(this); // Use the location here!!! }
LocationManager manager = (LocationManager) getActivity().getSystemService(Context.LOCATION_SERVICE); if (!manager.isProviderEnabled(LocationManager.GPS_PROVIDER) && !manager.isProviderEnabled(LocationManager.NETWORK_PROVIDER)) { locationEnabled = false; Toast.makeText(getActivity(), "Enable location services for accurate data", Toast.LENGTH_SHORT).show(); } else locationEnabled = true;
if (location != null) { Toast.makeText(getActivity(), "Location: " + location.getLatitude() + ", " + location.getLongitude(), Toast.LENGTH_SHORT).show(); } else if (location == null && locationEnabled) { locationClient.requestLocationUpdates(locationRequest, this); }
task.addOnSuccessListener(this, new OnSuccessListener<LocationSettingsResponse>() { @Override public void onSuccess(LocationSettingsResponse locationSettingsResponse) { // All location settings are satisfied. The client can initialize // location requests here. // ... } }); task.addOnFailureListener(this, new OnFailureListener() { @Override public void onFailure(@NonNull Exception e) { if (e instanceof ResolvableApiException) { // Location settings are not satisfied, but this can be fixed // by showing the user a dialog. try { // Show the dialog by calling startResolutionForResult(), // and check the result in onActivityResult(). ResolvableApiException resolvable = (ResolvableApiException) e; resolvable.startResolutionForResult(MainActivity.this, REQUEST_CHECK_SETTINGS); } catch (IntentSender.SendIntentException sendEx) { // Ignore the error. } } } });
private FusedLocationProviderClient fusedLocationClient; @Override protected void onCreate(Bundle savedInstanceState) { fusedLocationClient = LocationServices.getFusedLocationProviderClient(this); }