• 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Simple GeoLocation

#1
[eluser]Angilo[/eluser]
Simple GeoLocation is as it states a really simple geo location library which can be used for all kinds of purposes. Think about distribution, other location issues, et cetera.

It uses Google Maps to retrieve the longitude and latitude. Input can be anything, country, address, zip code, et cetera.

Credits are going to this blog (not mine), which I found useful (the code is coming from here):
http://www.snipe.net/2008/12/ip-geolocat...ch-in-php/

In this post I'll explain an example. We are a distribution company, and want every known store (in our database) in a radius of 500 km of this address.

To retrieve the latitude and longitude of our address, simply do

Code:
$this->geolocation->setAddress($locatie);
            
$Latitude   = $this->geolocation->getLattitude();
$Longitude  = $this->geolocation->getLongitude();

Let's prepare our query. The query will return all matches inside a rectangle, which obviously isn't our radius.

Create the rectangle:

Code:
$zcdRadius  = new RadiusCheck($Latitude, $Longitude, $Miles);
            
$minLat = $zcdRadius->MinLatitude();
$maxLat = $zcdRadius->MaxLatitude();
            
$minLong = $zcdRadius->MinLongitude();
$maxLong = $zcdRadius->MaxLongitude();

Add to the query:

Code:
$sql .= "latitude >= '".$minLat."' ";
$sql .= "AND latitude <= '".$maxLat."' ";
$sql .= "AND longitude >= '".$minLong."' ";
$sql .= "AND longitude <= '".$maxLong."'

All our results are inside the rectangle, to get the radius, we walk through our loop, with this code:

Code:
$zcdDistance = new DistanceCheck;
$Distance = $zcdDistance->Calculate($Latitude,$Longitude,$result['latitude'],$result['longitude']);
// Calculate to KM and use a factor
$DistanceKM = round(($Distance * 1.609344 * FACTOR_DISTANCE_ROAD),1);

if ($DistanceKM <= $maxDistance) {
// Do something with it
}

The distances are direct and therefor might be deviating from the real distance. Therefor I use the FACTOR_DISTANCE_ROAD. Care with this factor, it's variating per landscape type.

As you can see it's really simple, good luck.


The actual library:

Code:
&lt;?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');

class Geolocation {

    private $lattitude = '';
    private $longitude = '';
    
    function __construct()
    {
    }
    
    public function setAddress($address)
    {
        
        $geocode            = file_get_contents('http://maps.google.com/maps/api/geocode/json?address=' . $address . '&sensor=false');

        $output             = json_decode($geocode);

        $this->lattitude    = $output->results[0]->geometry->location->lat;
        $this->longitude    = $output->results[0]->geometry->location->lng;
    }
    
    public function getLattitude()
    {
        return $this->lattitude;
    }
    
    public function getLongitude()
    {
        return $this->longitude;
    }
    
}

class RadiusCheck extends GeoLocation {
    private $maxLat;
    private $minLat;
    private $maxLong;
    private $minLong;
    
    function RadiusCheck($Latitude, $Longitude, $Miles) {
        
        $EQUATOR_LAT_MILE = 69.172;
        
        $this->maxLat = $Latitude + $Miles / $EQUATOR_LAT_MILE;
        
        $this->minLat = $Latitude - ($this->maxLat - $Latitude);
        
        $this->maxLong = $Longitude + $Miles / (cos($this->minLat * M_PI / 180) * $EQUATOR_LAT_MILE);
        
        $this->minLong = $Longitude - ($this->maxLong - $Longitude);
        
    }
    
    function MaxLatitude() {
        
        return $this->maxLat;
        
    }
    
    function MinLatitude() {
        
        return $this->minLat;
        
    }
    
    function MaxLongitude() {
        
        return $this->maxLong;
        
    }
    
    function MinLongitude() {
        
        return $this->minLong;
        
    }
    
}

class DistanceCheck {
    
    function DistanceCheck() {
    }
    
    function Calculate(
        $dblLat1,
        $dblLong1,
        $dblLat2,
        $dblLong2
    ) {
        
        $EARTH_RADIUS_MILES = 3963;
        $dist = 0;
        //convert degrees to radians
        $dblLat1 = $dblLat1 * M_PI / 180;
        $dblLong1 = $dblLong1 * M_PI / 180;
        $dblLat2 = $dblLat2 * M_PI / 180;
        $dblLong2 = $dblLong2 * M_PI / 180;
        
        if ($dblLat1 != $dblLat2 && $dblLong1 != $dblLong2)
        {
            //the two points are not the same
            $dist =
            sin($dblLat1) * sin($dblLat2)
            + cos($dblLat1) * cos($dblLat2)
            * cos($dblLong2 - $dblLong1);
            $dist =
            $EARTH_RADIUS_MILES
            * (-1 * atan($dist / sqrt(1 - $dist * $dist)) + M_PI / 2);
        }
        return $dist;
    }
}

?&gt;


Digg   Delicious   Reddit   Facebook   Twitter   StumbleUpon  


  Theme © 2014 iAndrew  
Powered By MyBB, © 2002-2021 MyBB Group.