web-dev-qa-db-fra.com

Android: LocationManager vs Services Google Play

Je souhaite créer une application centrée sur l'obtention de la position actuelle de l'utilisateur, puis sur les points d'intérêt (bars, restaurants, etc.) proches de lui via le Google Places API.

En cherchant sur le Web un endroit pour commencer, je suis tombé sur des tutoriels qui utilisaient la classe LocationManager et sur d’autres qui utilisaient Services Google Play afin de trouver l’emplacement des utilisateurs.

À première vue, les deux font la même chose, mais comme je suis novice dans ce domaine, je suis un peu confuse et je ne sais pas quelle méthode convient le mieux à mes besoins. Alors, je veux vous demander:

Quelles sont les différences entre ces deux méthodes de recherche d'emplacements (le cas échéant)?

134
SoCo

Emplacement de l'utilisateur sur Android

Obtenir l'emplacement de l'utilisateur sur Android est un peu moins simple que sur iOS. Pour créer la confusion, il existe deux manières totalement différentes de le faire. Le premier utilise Android API de Android.location.LocationListener, et le second utilise les API de services Google Play com.google.Android.gms.location.LocationListener. Passons en revue les deux.

  1. API de localisation d’Android

    Les API de localisation d’Android utilisent trois fournisseurs différents pour obtenir la localisation:

    • LocationManager.GPS_PROVIDER - Ce fournisseur détermine la position à l'aide de satellites. Selon les conditions, ce fournisseur peut prendre un certain temps pour renvoyer un correctif d'emplacement.
    • LocationManager.NETWORK_PROVIDER - Ce fournisseur détermine l'emplacement en fonction de la disponibilité de la tour de téléphonie cellulaire et des points d'accès WiFi. Les résultats sont récupérés au moyen d'une recherche sur le réseau.
    • LocationManager.PASSIVE_PROVIDER - Ce fournisseur renvoie les emplacements générés par d'autres fournisseurs. Vous recevez passivement des mises à jour d'emplacement lorsque d'autres applications ou services le demandent, sans demander vous-même les emplacements.

En résumé, vous obtenez un objet de LocationManager du système, implémentez la LocationListener et appelez la requestLocationUpdates sur la LocationManager.

Voici un extrait de code:

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

Guide de l’API de Google sur les stratégies de localisation explique assez bien le code. Mais ils mentionnent également que dans la plupart des cas, vous obtiendrez de meilleures performances de la batterie, ainsi qu'une précision plus appropriée, en utilisant API de Google Location Services . Maintenant la confusion commence!

  1. API des services de localisation de Google

L’API des services de localisation de Google fait partie de l’API des services Google Play ( comment le configurer ). Ils sont construits sur l’API d’Android. Ces API fournissent un "fournisseur d'emplacement fusionné" au lieu des fournisseurs mentionnés ci-dessus. Ce fournisseur choisit automatiquement le fournisseur sous-jacent à utiliser, en fonction de la précision, de l'utilisation de la batterie, etc. Il est rapide car vous obtenez l'emplacement d'un service système qui le met à jour régulièrement. Et vous pouvez utiliser des fonctionnalités plus avancées telles que le geofencing.

Pour utiliser les services de localisation de Google, votre application doit se connecter au GooglePlayServicesClient. Pour vous connecter au client, votre activité (ou fragment, ou plus) doit implémenter les interfaces GooglePlayServicesClient.ConnectionCallbacks et GooglePlayServicesClient.OnConnectionFailedListener. Voici un exemple de code:

    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 
    }
  • Pourquoi locationClient.getLastLocation() est-il nul?

La locationClient.getLastLocation() obtient le dernier emplacement connu du client. Toutefois, le fournisseur d’emplacement fusionné ne conservera l’emplacement d’arrière-plan que si au moins un client y est connecté. Une fois le premier client connecté, il essaiera immédiatement d’obtenir un emplacement. Si votre activité est le premier client à vous connecter et que vous appelez getLastLocation() immédiatement dans onConnected(), le temps imparti au premier emplacement ne sera peut-être pas suffisant. Cela entraînera le locationnull.

Pour résoudre ce problème, vous devez attendre (indéterminément) que le fournisseur obtienne l’emplacement, puis appeler getLastLocation(), ce qui est impossible à connaître. Une autre (meilleure) option consiste à implémenter l'interface com.google.Android.gms.location.LocationListener pour recevoir des mises à jour d'emplacement périodiques (et à la désactiver dès que vous obtenez la première mise à jour).

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

Dans ce code, vous vérifiez si le client a déjà le dernier emplacement (dans onConnected). Sinon, vous demandez des mises à jour d'emplacement et désactivez les demandes (dans onLocationChanged() rappel) dès que vous recevez une mise à jour.

Notez que la locationClient.requestLocationUpdates(locationRequest, this); doit figurer dans le rappel onConnected, sinon vous obtiendrez un IllegalStateException, car vous tenterez de demander des emplacements sans connexion au client Google Play Services.

  • L'utilisateur a désactivé les services de localisation

Plusieurs fois, les services de localisation de l'utilisateur seraient désactivés (pour économiser la batterie ou pour des raisons de confidentialité). Dans un tel cas, le code ci-dessus demandera toujours des mises à jour d'emplacement, mais onLocationChanged ne sera jamais appelé. Vous pouvez arrêter les demandes en vérifiant si l'utilisateur a désactivé les services de localisation.

Si votre application nécessite d’activer les services de localisation, vous souhaitez afficher un message ou un toast. Malheureusement, il n’existe aucun moyen de vérifier si l’utilisateur a désactivé les services de localisation dans l’API des services de localisation de Google. Pour cela, vous devrez recourir à l’API d’Android.

Dans votre méthode 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;

Et utilisez le drapeau locationEnabled dans votre méthode onConnected comme ceci:

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

merci à Rahul Jiresal

UPDATE

Le document est mis à jour, LocationClient est supprimé et l’API prend en charge l’activation du GPS en un clic depuis la boîte de dialogue:

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

Lien https://developer.Android.com/training/location/change-location-settings#Prompt

Nouveau client d'emplacement: FusedLocationProviderClient

  private FusedLocationProviderClient fusedLocationClient;

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

Il est recommandé de passer https://developer.Android.com/training/location avant de commencer toute tâche de localisation.

302
pRaNaY

D'après mon expérience, "exactitude plus appropriée" ne signifie en aucun cas mieux. Sauf si quelque chose me manque, si vous voulez vous assurer que le GPS est utilisé, LocationManager est la seule solution. Nous suivons les véhicules avec notre application et, encore une fois, à moins que quelque chose ne me manque, les services Google Play fournissent assez souvent des lieux très inexacts.

29
Kit

Vous devez utiliser l’API de localisation des services Google Play au lieu de LocationManager. Selon les docs:

Les API de localisation des services Google Play sont privilégiées par rapport aux Android API de localisation (Android.location) comme moyen de renforcer la reconnaissance de la localisation de votre application. Si vous utilisez actuellement les API d'emplacement du cadre Android, nous vous encourageons vivement à basculer sur les API d'emplacement des services Google Play dès que possible.

Quant à savoir pourquoi changer, Google dit ceci:

L'API des services de localisation de Google, qui fait partie des services Google Play, fournit un cadre de haut niveau plus puissant qui gère automatiquement les fournisseurs de localisation, les déplacements des utilisateurs et la précision de la localisation. Il gère également la planification des mises à jour d'emplacement en fonction des paramètres de consommation d'énergie fournis. Dans la plupart des cas, vous obtiendrez de meilleures performances de la batterie, ainsi qu'une précision plus appropriée, en utilisant l'API Services de localisation.

26
NoChinDeluxe

J'utilise l'API Google Location Services depuis un certain temps. Il présente des avantages car il présente la complexité de disposer de plusieurs sources pour déterminer les positions. Cependant, il encapsule trop fortement , de sorte que lorsque vous obtenez une position étrange, vous n’avez aucun moyen de déterminer l’origine de cette position.

Dans la vie réelle, plusieurs valeurs étranges sont apparues, à 10 kilomètres de la position réelle. La seule explication est que ces emplacements loufoques proviennent d'erreurs dans les bases de données Wi-Fi ou NWK de Googles - erreurs qui resteront toujours d'actualité, car les topologies Wi-Fi et réseau changent chaque jour. Mais malheureusement (et étonnamment), l’API ne vous donne aucune information sur la façon dont une position individuelle a été dérivée.

enter image description here

Cela vous laisse avec les problèmes de filtrer les valeurs anormales basées sur le contrôle de vraisemblance de la vitesse, l'accélération, le relèvement, etc.

... ou revenez à la bonne vieille API de framework et utilisez uniquement le GPS, ce que j'ai décidé de faire jusqu'à ce que Google améliore l'API fusionnée.

21
j3App

L'API des services de localisation de Google , qui fait partie des services de Google Play, fournit des cadre qui gère automatiquement les fournisseurs d’emplacement , le mouvement des utilisateurs et la précision de l’emplacement . Il gère également la planification des mises à jour d'emplacement en fonction des paramètres de consommation d'énergie fournis. Dans la plupart des cas, vous obtiendrez de meilleures performances de la batterie , ainsi qu'une précision plus appropriée, par en utilisant l'API Services de localisation.

Différences plus détaillées entre les deux apis API Google Play Service Service et API Android Framework Location peut être trouvé ici

7
Dhruvam Gupta

Oui, l'API Services de localisation des services Google Play peut donner des informations de localisation très trompeuses. Les modems WiFi sont déplacés, les modems WiFi sont mis à jour avec des informations de localisation incorrectes (c'est-à-dire si la localisation est falsifiée par un périphérique Android qui met à jour la position du modem WiFi) et qu'il existe de nombreuses autres circonstances susceptibles de générer des données de localisation incorrectes. Triangulation modem WiFi. Dans toutes nos applications où la localisation précise est obligatoire, nous utilisons uniquement le GPS.

1
user1608385

Différences entre les deux apis API Google Play Service Location et Android API Framework Location basée sur service GPS

FusedLocationProviderClient

  1. Pour la 1ère extraction, l'emplacement ne doit pas être null (c'est-à-dire: une autre application doit mettre à jour l'emplacement Lastknown dans la base de données GoogleplayService. S'il est null, il faut contourner le problème).
  2. Pour l'extraction séquentielle suivante, il utilise la méthode requestLocationUpdates() pour extraire l'emplacement.
  3. La localisation est basée uniquement sur locationRequest.setInterval(milliseconds)et setFastestInterval(milliseconds), pas sur changement de localisation de l'utilisateur
  4. La valeur LatLng renvoyée a contient seulement 7 valeurs décimales (par exemple: 11.9557996, 79.8234599), pas aussi précise
  5. Recommandé, lorsque les exigences de votre application correspondent à l'emplacement actuel distance négligeable de (précision de 50 à 100 mètres)
  6. Efficace dans l'utilisation de la batterie.

LocationManager Api

  1. La récupération de l'emplacement de l'utilisateur est appelée à l'aide de locationManager.requestLocationUpdates ()
  2. La localisation récupérée en fonction de l'utilisateur changement d'emplacement et intervalles de tempslocationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, milliseconds, mindistance, Mylocationlistener)

  3. La valeur LatLng renvoyée contient (14 valeurs décimales(par exemple: 11.94574594963342 79.81166719458997))valeurs de localisation précises

  4. Recommandé pour une application basée sur la localisation, lorsque vous avez besoin de plus de précision, même en mètres.
  5. L'utilisation de la batterie est basée sur intervalle d'extraction et distance d'extraction.
0
Sackurise

LocationManager

Comme indiqué dans la documentation officielle , cette classe vous permet d'utiliser les services pour un emplacement, de mettre à jour périodiquement la position géographique de l'appareil ou d'envoyer "Intent" à des applications, afin de dire que l'appareil est près de l'emplacement prédéterminé. L'API nécessite ACCESS_COARSE_LOCATION ou ACCESS_FINE_LOCATION

Services Google Location API

Il est totalement incompatible avec LocationManager, mais en ce qui concerne le fonctionnement en temps réel, il existe certaines différences fondamentales.

Avantages et inconvénients

En ce qui concerne les services Google Location API, comparés à LocationManager, nous avons constaté une augmentation significative des performances et de la stabilité lors de l’utilisation. Par exemple, il y avait un problème courant avec LocationManager qui recevait des emplacements précédents ou des mises à jour de carte, lorsque des paramètres avaient été définis pour la période minimale et la distance minimale à partir desquelles le périphérique devait être déplacé pour les mises à jour ultérieures; l'un des paramètres était généralement ignoré. Dans les services API Google Location, ce problème n'a pas été rencontré. En outre, les services de localisation de Google consomment moins de poudre de batterie.

En conséquence, les services Google Location API ont obtenu de meilleurs résultats dans tous les cas. Cependant, il y a aussi quelques inconvénients. Pour utiliser les services de localisation, vous devez installer les services Google Play.

Par conséquent, l'application ne fonctionnera pas sur les appareils dotés d'un micrologiciel habituel non pris en charge par Google ou sur lesquels Google Services n'est pas disponible. C'est un point très important qu'il faut prendre en compte. Les recherches dans ce domaine ont révélé le fait que la plupart des utilisateurs ne disposent pas des services Google Play. Par exemple, ils ne sont pas disponibles en Chine en raison de la politique nationale, et il s’agit d’une partie importante du marché qui ne peut être ignorée. Dans ce cas, il est nécessaire de se tourner vers LocationManager.

Les services API Google Location sont la meilleure solution pour utiliser des cartes. Cette API vous permet de travailler avec les coordonnées les plus précises et avec des dépenses minimales en termes de ressources mobiles, tant que l'utilisateur a installé les services Google Play. sinon, la seule solution est LocationManager.

Lire la suite ici

0
yoAlex5