The geoDistance php function will allow you to compute the distance between two latitude/longitude coordinates on Earth. It utilizes the mean earth radius for the WGS84 ellipsoid as defined in the 1984 World Geodetic System which is a standard for use in cartography, geodesy, and satellite navigation including GPS.

By default the distance is returned in statute miles, but you can also return it in nautical miles, kilometers, meters, or feet.

/**
 * Geographic Distance - Calculates the distance between two GPS coordinates provided the latitude and longitude of
 * those points.
 *
 * This function uses the Great-circle distance formula which is the shortest distance between two points on the surface
 * of a sphere. Use positive latitude values for northern hemisphere, and negative latitude values for southern
 * hemisphere. Use positive longitude values for eastern hemisphere, and negative longitude values for western
 * hemisphere. For example the coordinates for Seattle, WA would be 47.608013 latitude, -122.335167 longitude.
 *
 * @see https://en.wikipedia.org/wiki/Great-circle_distance#Formulas
 *
 * @param float $latitude1 The latitude of the first GPS coordinate
 * @param float $longitude1 The longitude of the first GPS coordinate
 * @param float $latitude2 The latitude of the second GPS coordinate
 * @param float $longitude2 The longitude of the second GPS coordinate
 * @param string|null $returnUnit Default is statute miles. m = meters, km = kilometers, nm = nautical miles, f = feet
 * @return float Returns the distance expressed in unit of type $returnUnit
 */
function geoDistance($latitude1, $longitude1, $latitude2, $longitude2, $returnUnit = null): float
{
    // Earth radius is 6378 km at equator, 6356 km at poles. Mean earth radius is 6371.0088 km
    $earthRadius = 6371.0088;

    $phi1 = deg2rad($latitude1);
    $phi2 = deg2rad($latitude2);
    $deltaLambda = deg2rad($longitude1 - $longitude2);

    // min and max solves floating precision issues and rounding with PHP that could cause acos to return NaN values
    $deltaSigma = acos(min(max(sin($phi1) * sin($phi2) + cos($phi1) * cos($phi2) * cos($deltaLambda), -1.0), 1.0));

    $distanceInKm = $earthRadius * $deltaSigma;

    if ($returnUnit === 'm') {
        return $distanceInKm * 1000;
    } else if ($returnUnit === 'km') {
        return $distanceInKm;
    } else if ($returnUnit === 'nm') {
        return $distanceInKm / 1.852;
    } else if ($returnUnit === 'f') {
        return $distanceInKm * 5280;
    }

    // return in statute miles (sm) by default
    return $distanceInKm / 1.609344;
}

This code snippet was published on It was last edited on

0

0 Comments

  • Votes
  • Oldest
  • Latest