Géolocalisation et distance avec OpenStreetMap

10 juillet 2018 - : Javascript jQuery PHP API - : Pas de commentaire

Géolocalisation et distance avec OpenStreetMap

Dans certaines utilisations de la géolocalisation, il peut s'avérer nécessaire d'afficher les points situés à une certaine distance de l'utilisateur ou d'une ville.

Ceci fait intervenir différents critères que nous allons détailler.

Géolocaliser l'utilisateur

Avant toute chose, ATTENTION, la géolocalisation de l'utilisateur ne peut se faire sans son consentement.

Ceci étant dit, les navigateurs affichent maintenant une alerte lorsqu'un site tente d'accéder à la localisation du visiteur.

Deuxième chose, la géolocalisation fonctionnera uniquement en HTTPS, ou en local.

Le script à insérer dans vos pages pour activer cette géolocalisation est assez simple.

function geoloc(){ // ou tout autre nom de fonction
    var geoSuccess = function(position) { // Ceci s'exécutera si l'utilisateur accepte la géolocalisation
        startPos = position;
        userlat = startPos.coords.latitude;
        userlon = startPos.coords.longitude;
        console.log("lat: "+userlat+" - lon: "+userlon);
    };
    var geoFail = function(){ // Ceci s'exécutera si l'utilisateur refuse la géolocalisation
        console.log("refus");
    };
    // La ligne ci-dessous cherche la position de l'utilisateur et déclenchera la demande d'accord
    navigator.geolocation.getCurrentPosition(geoSuccess,geoFail);
}

Voilà, c'est tout :-)

Trouver les coordonnées GPS d'une ville (ou d'une adresse, par extension)

Si vous souhaitez donner à l'utilisateur l'opportunité d'entrer une ville, ou une adresse, OpenStreetMap vous en donne la possibilité.

Le service Nominatim est là pour ça. Ce service, interrogeable par Ajax, vous permet de faire des recherches par commune ou par adresse, entre autres.

Pour interroger le service, envoyer une requête GET qui intègre l'adresse complète et les options éventuelles (une documentation complète de Nominatim est disponible)

Dans notre exemple, nous allons considérer que nous avons un champ de saisie appelé "ville" qui permet à l'utilisateur de saisir le nom d'une ville dans notre formulaire. Puis, un clic sur un bouton permet de rechercher les coordonnées.

function chercher(){
    var ville = $("#ville").val();
    if(ville != ""){
        $.ajax({
            url: "https://nominatim.openstreetmap.org/search", // URL de Nominatim
            type: 'get', // Requête de type GET
            data: "q="+ville+"&format=json&addressdetails=1&limit=1&polygon_svg=1" // Données envoyées (q -> adresse complète, format -> format attendu pour la réponse, limit -> nombre de réponses attendu, polygon_svg -> fournit les données de polygone de la réponse en svg)
        }).done(function (response) {
            if(response != ""){
                userlat = response[0]['lat'];
                userlon = response[0]['lon'];
            }                
        }).fail(function (error) {
            alert(error);
        });      
    }
}

Avec ce code, nous récupérons les coordonnées de latitude et longitude du centre ville.

Sélectionner les points situés à une certaine distance d'une coordonnée

Lors d'une recherche, il peut être utile de récupérer les points situés à quelques kilomètres de distance, par exemple, d'un point central.

Ainsi, si nous possédons la latitude et la longitude d'une personne ou d'une ville, nous pourrons récupérer les points situés à l'intérieur d'un cercle dont le rayon sera de quelques kilomètres à partir de cette personne.

Posons les bases :

  • Nous avons une liste de points en base de données (latitude et longitude)
  • Nous avons géolocalisé le point central sous les noms userlat et userlon
  • Nous avons récupéré la distance souhaitée dans une variable distance

Sur ces bases, nous allons interroger notre base de données, avec Ajax, afin de récupérer les points dont les coordonnées seront à l'intérieur du cercle.

Voici le Javascript

function cercle(){ // Ou tout autre nom de fonction
    var distance = $("#distance").val(); // Nous récupérons la distance
    $.ajax({
        url:'http://localhost/carte/cherchevilles.php',
        type: 'POST',
        data: 'lat='+userlat+'&lon='+userlon+'&distance='+distance
    }).done(function(reponse){
        var points = JSON.parse(reponse);
        // Ici nous traitons les différents points
    }).fail (function(error){
        console.log(error);
    });
}

Bien sûr, nous avons besoin d'exécuter la requête SQL pour récupérer les points en base de données.

Voici le PHP

<?php
header('Access-Control-Allow-Origin: *');
require_once("connect.php");
if($_POST['distance'] != 0){
	$distance = $_POST['distance'];
}else{
	$distance=1500; // définition d'une distance par défaut
}

// Préparation de la requête SQL. Celle-ci sélectionnera tous les points dont la "distance" sera inférieure à la distance choisie par l'utilisateur
// Cette distance est issue du calcul commençant par 6371, qui permet de travailler en kilomètres
$sql = "SELECT id, nom, lat, lon, ( 6371 * acos( cos( radians(".$_POST['lat'].") ) * cos( radians( lat ) ) * cos( radians( lon ) - radians(".$_POST['lon'].") ) + sin( radians(".$_POST['lat'].") ) * sin( radians( lat ) ) ) ) AS distance FROM points HAVING distance < ".$distance." ORDER BY distance";

$query = $db->prepare($sql);
$query->execute();
$result = $query->fetchAll();
echo json_encode($result);

require_once("close.php");

Commentaires

Pas encore de commentaire

Laisser un commentaire