Vous êtes prêt !

Pour passer à l'étape de développement, accédez à notre documentation pour les développeurs.

Activer Google Maps Roads API

Pour commencer, nous allons vous guider à travers la console Google Developers et effectuer deux ou trois petites choses :

  1. Créer ou sélectionner un projet
  2. Activer Google Maps Roads API
  3. Créer les clés appropriées
Continuer

Concepts avancés

Remarque : Les exemples ci-dessous utilisent Google Maps Roads API dans Java Client for Google Maps Services. Vous pouvez adapter les concepts au langage de votre choix. Les clients Python Client, Go Client et Node.js Client sont également disponibles sur GitHub.

Acquérir des données

Il existe plusieurs manières d'obtenir des données de géolocalisation collectées. Deux techniques d'acquisition des données à utiliser avec la fonctionnalité Snap to Roads de Google Maps Roads API sont décrites ici.

GPX

GPX est un format XML ouvert permettant de partager des routes, des parcours et des points de cheminement capturés par les GPS. Cet exemple utilise l'analyseur XmlPull, un analyseur XML léger disponible pour le serveur Java et les environnements mobiles.

/**
 * Parses the waypoint (wpt tags) data into native objects from a GPX stream.
 */
private List<LatLng> loadGpxData(XmlPullParser parser, InputStream gpxIn)
        throws XmlPullParserException, IOException {
    // We use a List<> as we need subList for paging later
    List<LatLng> latLngs = new ArrayList<>();
    parser.setInput(gpxIn, null);
    parser.nextTag();

    while (parser.next() != XmlPullParser.END_DOCUMENT) {
        if (parser.getEventType() != XmlPullParser.START_TAG) {
            continue;
        }

        if (parser.getName().equals("wpt")) {
            // Save the discovered latitude/longitude attributes in each <wpt>.
            latLngs.add(new LatLng(
                    Double.valueOf(parser.getAttributeValue(null, "lat")),
                    Double.valueOf(parser.getAttributeValue(null, "lon"))));
        }
        // Otherwise, skip irrelevant data
    }

    return latLngs;
}

Voici des données GPX brutes chargées sur une carte.

Données GPX brutes sur une carte

Services de géolocalisation Android

La meilleure méthode pour capturer des données GPS transmises par un appareil Android dépend de votre cas d'utilisation. Consultez la formation Android sur la Réception d'actualisations de géolocalisation ainsi que les échantillons de gélocalisation Google Play sur GitHub.

Traiter des tracés longs

Puisque la fonctionnalité Snap to Roads déduit la géolocalisation en fonction du tracé complet, plutôt que sur la base de points séparés, vous devez faire attention lors du traitement de tracés longs (c'est-à-dire, des tracés dépassant la limite de 100 points par requête).

Pour traiter les requêtes individuelles sous la forme d'un tracé long, vous devez inclure un chevauchement, de façon à inclure les points finaux de la requête précédente en tant que premiers points de la requête suivante. Le nombre de points à inclure dépend de la précision de vos données. Il est recommandé d'inclure plus de points pour les requêtes peu précises.

L'exemple suivant utilise Java Client for Google Maps Services pour envoyer des requêtes paginées, puis relie les données dans la liste renvoyée en incluant les points interpolés.

/**
 * Snaps the points to their most likely position on roads using the Roads API.
 */
private List<SnappedPoint> snapToRoads(GeoApiContext context) throws Exception {
    List<SnappedPoint> snappedPoints = new ArrayList<>();

    int offset = 0;
    while (offset < mCapturedLocations.size()) {
        // Calculate which points to include in this request. We can't exceed the API's
        // maximum and we want to ensure some overlap so the API can infer a good location for
        // the first few points in each request.
        if (offset > 0) {
            offset -= PAGINATION_OVERLAP;   // Rewind to include some previous points.
        }
        int lowerBound = offset;
        int upperBound = Math.min(offset + PAGE_SIZE_LIMIT, mCapturedLocations.size());

        // Get the data we need for this page.
        LatLng[] page = mCapturedLocations
                .subList(lowerBound, upperBound)
                .toArray(new LatLng[upperBound - lowerBound]);

        // Perform the request. Because we have interpolate=true, we will get extra data points
        // between our originally requested path. To ensure we can concatenate these points, we
        // only start adding once we've hit the first new point (that is, skip the overlap).
        SnappedPoint[] points = RoadsApi.snapToRoads(context, true, page).await();
        boolean passedOverlap = false;
        for (SnappedPoint point : points) {
            if (offset == 0 || point.originalIndex >= PAGINATION_OVERLAP - 1) {
                passedOverlap = true;
            }
            if (passedOverlap) {
                snappedPoints.add(point);
            }
        }

        offset = upperBound;
    }

    return snappedPoints;
}

Voici les données ci-dessus après avoir exécuté les requêtes Snap to Roads. La ligne rouge représente les données brutes et la ligne bleue correspond aux données alignées.

Exemple de données balisées sur les routes

Utiliser le quota de manière efficace

La réponse à une requête Snap to Roads inclut une liste d'identifiants de lieu qui renvoient vers les points que vous avez fournis, potentiellement avec des points supplémentaires si vous avez défini interpolate=true.

Pour utiliser efficacement votre quota autorisé pour une requête de limites de vitesse, vous devez demander uniquement des identifiants de lieux uniques dans votre requête. Cet exemple utilise Java Client for Google Maps Services pour envoyer une requête de limites de vitesse à partir d'une liste d'identifiants de lieux.

/**
 * Retrieves speed limits for the previously-snapped points. This method is efficient in terms
 * of quota usage as it will only query for unique places.
 *
 * Note: Speed limit data is only available for requests using an API key enabled for a
 * Google Maps APIs Premium Plan license.
 */
private Map<String, SpeedLimit> getSpeedLimits(GeoApiContext context, List<SnappedPoint> points)
        throws Exception {
    Map<String, SpeedLimit> placeSpeeds = new HashMap<>();

    // Pro tip: Save on quota by filtering to unique place IDs.
    for (SnappedPoint point : points) {
        placeSpeeds.put(point.placeId, null);
    }

    String[] uniquePlaceIds =
            placeSpeeds.keySet().toArray(new String[placeSpeeds.keySet().size()]);

    // Loop through the places, one page (API request) at a time.
    for (int i = 0; i < uniquePlaceIds.length; i += PAGE_SIZE_LIMIT) {
        String[] page = Arrays.copyOfRange(uniquePlaceIds, i,
                Math.min(i + PAGE_SIZE_LIMIT, uniquePlaceIds.length));

        // Execute!
        SpeedLimit[] placeLimits = RoadsApi.speedLimits(context, page).await();
        for (SpeedLimit sl : placeLimits) {
            placeSpeeds.put(sl.placeId, sl);
        }
    }

    return placeSpeeds;
}

Voici les données ci-dessus avec l'indication des limites de vitesse pour chaque identifiant de lieu unique.

Panneaux de limitation de vitesse sur une carte

Interagir avec d'autres API

L'un des avantages du renvoi des identifiants de lieux dans les réponses de Snap to Roads est la possibilité de les utiliser sur de nombreuses Google Maps API. Cet exemple utilise Java Client for Google Maps Services pour géocoder un lieu renvoyé à partir de la requête Snap to Road ci-dessus.

/**
 * Geocodes a snapped point using the place ID.
 */
private GeocodingResult geocodeSnappedPoint(GeoApiContext context, SnappedPoint point) throws Exception {
    GeocodingResult[] results = GeocodingApi.newRequest(context)
            .place(point.placeId)
            .await();

    if (results.length > 0) {
        return results[0];
    }
    return null;
}

Ici, l'adresse de Google Maps Geocoding API a été ajoutée au marqueur de limitation de vitesse.

Adresse géocodée affichée sur un marqueur

Échantillon de code

À savoir

Le code utilisé pour cet article est disponible sous forme d'application Android unique à des fins d'illustration. En pratique, vous ne devez pas distribuer vos clés d'API côté serveur dans une application Android car votre clé ne peut pas être protégée contre les accès non autorisés de tiers. Pour sécuriser vos clés, vous devez donc déployer le code interagissant avec l'API en tant que proxy côté serveur et faire en sorte que votre application Android envoie des requêtes via ce proxy afin de garantir qu'elles sont autorisées.

Téléchargement

Téléchargez le code à partir de GitHub.

Envoyer des commentaires concernant…

Google Maps Roads API
Google Maps Roads API
Besoin d'aide ? Consultez notre page d'assistance.