IT

Android : LocationManager 및 Google Play 서비스

lottoking 2020. 6. 25. 07:42
반응형

Android : LocationManager 및 Google Play 서비스


사용자의 현재 위치를 얻는 데 중점을 둔 앱을 만들고 Google Places API 를 통해 자신과 가까운 관심 지점 (예 : 바, 레스토랑 등)을 찾고 싶습니다 .

시작할 장소를 웹에서 검색 할 때 LocationManager클래스 를 사용하는 일부 자습서 사용자 위치를 찾기 위해 Google Play 서비스 를 사용하는 일부 자습서를 보았습니다.

첫눈에 두 사람 모두 같은 일을하지만, 이것에 익숙하지 않아서 약간 혼란 스러웠으며 어떤 방법이 내 요구에 가장 적합한 지 알 수 없습니다. 그래서 나는 당신에게 묻고 싶습니다 :

위치를 찾는 두 가지 방법의 차이점은 무엇입니까?


Android의 사용자 위치

안드로이드에서 사용자의 위치를 ​​얻는 것은 iOS보다 덜 간단합니다. 혼란을 시작하기 위해 완전히 다른 두 가지 방법이 있습니다. 첫 번째는의 Android API를 사용 android.location.LocationListener하고 두 번째는 Google Play Services API를 사용하는 것 com.google.android.gms.location.LocationListener입니다. 두 가지를 모두 살펴 보자.

  1. 안드로이드의 위치 API

    Android의 위치 API는 세 가지 다른 제공 업체를 사용하여 위치를 얻습니다.

    • LocationManager.GPS_PROVIDER—이 공급자는 위성을 사용하여 위치를 결정합니다. 조건에 따라이 공급자는 위치 수정을 반환하는 데 시간이 걸릴 수 있습니다.
    • LocationManager.NETWORK_PROVIDER—이 공급자는 셀 타워 및 WiFi 액세스 포인트의 가용성에 따라 위치를 결정합니다. 결과는 네트워크 조회를 통해 검색됩니다.
    • LocationManager.PASSIVE_PROVIDER—이 제공자는 다른 제공자가 생성 한 위치를 반환합니다. 다른 응용 프로그램이나 서비스가 실제로 위치를 직접 요청하지 않고 요청하면 위치 업데이트를 수동으로받습니다.

요점은 LocationManager시스템에서 객체를 가져 와서 구현 LocationListener하고를 호출한다는 requestLocationUpdatesLocationManager입니다.

다음은 코드 스 니펫입니다.

    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);

위치 전략에 대한 Google API 가이드 는 코드를 매우 잘 설명합니다. 그러나 대부분의 경우 Google 위치 서비스 API를 대신 사용하면 배터리 성능이 향상되고 정확성이 향상 됩니다. 이제 혼란이 시작됩니다!

  1. Google의 위치 서비스 API

Google의 위치 서비스 API는 Google Play 서비스 APK의 일부입니다 ( 설정 방법 ). 그것들은 Android API 위에 구축되었습니다. 이 API는 위에서 언급 한 공급자 대신 "퓨즈 위치 공급자"를 제공합니다. 이 공급자는 정확도, 배터리 사용량 등을 기준으로 사용할 기본 공급자를 자동으로 선택합니다. 시스템 전체 서비스에서 위치를 지속적으로 업데이트하여 업데이트하므로 속도가 빠릅니다. 지오 펜싱과 같은 고급 기능을 사용할 수 있습니다.

Google의 위치 서비스를 사용하려면 앱이에 연결되어 있어야합니다 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()null입니까?

locationClient.getLastLocation()클라이언트에서 마지막으로 알려진 위치를 가져옵니다. 그러나 Fused Location Provider는 하나 이상의 클라이언트가 연결된 경우에만 백그라운드 위치를 유지합니다. 첫 번째 클라이언트가 연결되면 즉시 위치를 가져 오려고 시도합니다. 당신의 활동이 연결하는 첫 번째 클라이언트이며 호출하면 getLastLocation()즉시에서 onConnected()첫 번째 위치에 올 수있는 충분한 시간이되지 않을 수도.이 발생합니다 location되고 null.

이 문제를 해결하려면 공급자가 위치 getLastLocation()를 파악할 때까지 (불확실하게) 기다렸다가을 호출 해야합니다. 또 다른 (더 나은) 옵션은 com.google.android.gms.location.LocationListener주기적 위치 업데이트를 수신 하도록 인터페이스 를 구현하는 것입니다 (첫 번째 업데이트를 받으면 끄십시오).

    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!!!
    }

이 코드에서는 클라이언트에 이미 마지막 위치 ( onConnected) 가 있는지 확인합니다 . 그렇지 않은 경우 위치 업데이트를 요청하고 업데이트를 받으면 onLocationChanged()즉시 콜백으로 요청을 끕니다 .

(가) 참고 locationClient.requestLocationUpdates(locationRequest, this);가이 안에 있어야하는 onConnected콜백, 그렇지 않으면 당신은 얻을 것이다 IllegalStateException당신은 구글 플레이 서비스 클라이언트에 연결하지 않고 위치에 대한 요청하려고 할 것이기 때문에.

  • 사용자가 위치 서비스를 사용 중지했습니다

많은 경우에 사용자는 배터리를 절약하거나 개인 정보 보호를 위해 위치 서비스를 비활성화했습니다. 이 경우 위의 코드는 여전히 위치 업데이트를 요청하지만 onLocationChanged호출되지는 않습니다. 사용자가 위치 서비스를 비활성화했는지 확인하여 요청을 중지 할 수 있습니다.

앱에서 위치 서비스를 활성화해야하는 경우 메시지 또는 토스트를 표시하려고합니다. 안타깝게도 사용자가 Google의 위치 서비스 API에서 위치 서비스를 사용 중지했는지 확인하는 방법은 없습니다. 이를 위해서는 Android API를 사용해야합니다.

당신의 onCreate방법에서 :

    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;

그리고 메소드 locationEnabled에서 다음 onConnected과 같이 플래그를 사용하십시오 .

    if (location != null) {
    Toast.makeText(getActivity(), "Location: " + location.getLatitude() + ", " + location.getLongitude(), Toast.LENGTH_SHORT).show();
}
else if (location == null && locationEnabled) {
    locationClient.requestLocationUpdates(locationRequest, this);
}

Rahul Jiresal 덕분에

최신 정보

대화 상자에서 한 번의 클릭으로 문서가 업데이트되고 LocationClient가 제거되고 API가 GPS를 활성화하도록 지원합니다.

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.
            }
        }
    }
});

링크 https://developer.android.com/training/location/change-location-settings#prompt

새로운 위치 클라이언트 : FusedLocationProviderClient

  private FusedLocationProviderClient fusedLocationClient;

@Override
protected void onCreate(Bundle savedInstanceState) {
    fusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
}

위치 작업을 수행하기 전에 https://developer.android.com/training/location 을 방문하는 것이 좋습니다 .


In my experience, "more appropriate accuracy" doesn't mean better by any means. Unless I'm missing something, if you want to make sure GPS is used, LocationManager is the only way to go. We track vehicles with our app and, again, unless I'm missing something, Google Play Services provides some very inaccurate locations quite often.


You should use the Google Play Services location api instead of LocationManager. According to the docs:

The Google Play services location APIs are preferred over the Android framework location APIs (android.location) as a way of adding location awareness to your app. If you are currently using the Android framework location APIs, you are strongly encouraged to switch to the Google Play services location APIs as soon as possible.

As to why to switch, Google says this:

The Google Location Services API, part of Google Play Services, provides a more powerful, high-level framework that automatically handles location providers, user movement, and location accuracy. It also handles location update scheduling based on power consumption parameters you provide. In most cases, you'll get better battery performance, as well as more appropriate accuracy, by using the Location Services API.


I have been using the Google Location Services API for quite a while. It does have advantages, since it encapsulates the complexity of having several sources for determining positions. However it encapsulates too heavily, so that when you get a strange position, you have no way to determine where that strange position came from.

In real life I have had several freak values pop up, being 10's of kilometers away from the actual position. The only explanation is that these crazy locations stem from errors in Googles Wi-Fi or NWK databases - errors which will always be there, since Wi-Fi and Network topologies change every day. But unfortunately (and surprisingly) the API gives you no information as to how an individual position was derived.

enter image description here

This leaves you with the problems of having to filter out freak values based on plausibility checking on speed, accelleration, bearing etc.

... or go back to the good old framework API and use GPS only, which is what I decided to do until Google improves the fused API.


The Google Location Services API, part of Google Play Services, provides a more powerful, high-level framework that automatically handles location providers, user movement, and location accuracy. It also handles location update scheduling based on power consumption parameters you provide. In most cases, you’ll get better battery performance, as well as more appropriate accuracy, by using the Location Services API.

More detailed diffferences between the two apis Google Play Service Location API and Android Framework Location API can be found here


Yes, the Google Play Services Location Services API can give very misleading Location info. WiFi modems get moved, WiFi modems get updated with incorrect location information (ie if location is spoofed by an Android device that updates the WiFi modem's location) and there are a host of other circumstances that can result in incorrect Location data from WiFi modem triangulation. In all our apps where precise Location is mandatory, we use GPS only.


Diffferences between the two apis Google Play Service Location API and Android Framework Location API based on GPS service

FusedLocationProviderClient

  1. For the 1st fetch, the location must not be null(i.e: Some other app need to update the Lastknown location in the GoogleplayService database. if it is null, need work around)
  2. For the next sequential Fetch, it uses requestLocationUpdates() method to fetch the location.
  3. The location fetch is only based on locationRequest.setInterval(milliseconds)and setFastestInterval(milliseconds), not based on user location change
  4. The LatLng value returned has contain only 7 decimal values (e.g: 11.9557996, 79.8234599), not as accurate
  5. Recommended, when your app requirement takes current location distance negligible of (50 - 100 meters accuracy)
  6. Effective in Battery usage.

LocationManager Api

  1. The user location fetch is invoked using locationManager.requestLocationUpdates()
  2. The location fetch based on user location change and time intervals locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, milliseconds, mindistance, Mylocationlistener)

  3. The LatLng value returned has contain 14 decimal values (e.g: 11.94574594963342 79.81166719458997) accurate location values

  4. Recommended for location based app, when needs more accuracy even in meters.
  5. Battery usage is based on fetch interval and fetch distance.

LocationManager

As stated in the official documentation, this class allows you to use the services for a location, periodically update the geographic position of the device or send “Intent” to apps, in order to say that the device is near the predetermined location. API require ACCESS_COARSE_LOCATION or ACCESS_FINE_LOCATION

Google Location API Services

It is fully inconsistent with LocationManager, but as for the real-time functioning there are some fundamental differences.

Advantages and disadvantages

As for Google Location API Services, if we compare it with LocationManager, we noticed significantly increased performance and stability during use. For example, there was a common problem with LocationManager receiving previous locations or map updates, when parameters had been set for the minimum period of time and distance by which the device must be displaced for subsequent updates; one of the parameters was usually ignored. In Google Location API Services, this problem was not encountered. Also, Google Location Services consume less battery powder.

As a result, Google Location API Services performed better in all cases. However, there are also some disadvantages. To use Location Services, you should install Google Play Services.

Therefore, in devices with usual firmware that are not supported by Google or in which Google Services are unavailable, the application will not work. This is a very important point that must be taken into account. Research into this area uncovered the fact that most users do not have Google Play Services. For example, they are not available in China due to the national policy, and this is a significant part of the market that cannot be ignored. In this case, it is necessary to turn to LocationManager.

Google Location API Services is the best solution for working with maps. This API allows you to work with the most accurate coordinates and with minimal expenses in terms of mobile resources, as long as the user has installed Google Play Services; otherwise, the only solution is LocationManager.

Read more here

참고URL : https://stackoverflow.com/questions/33022662/android-locationmanager-vs-google-play-services

반응형