/**
*
*/
package ecologylab.bigsemantics.sensing;
import ecologylab.bigsemantics.metadata.builtins.GisLocation;
import ecologylab.generic.Debug;
import ecologylab.sensor.location.EarthData;
/**
* Methods for computing on GisLocation and other location-based stuff.
*
* @author andruid
*/
public class GisTools extends Debug implements EarthData
{
/**
*
*/
public GisTools()
{
}
public GisLocation constructGisLocation(double lat, double lon, double alt)
{
GisLocation result = new GisLocation();
result.setLatitude(lat);
result.setLongitude(lon);
result.setAltitude(alt);
return result;
}
/**
* Get the set of coordinates, serialized for use in KML / Google Earth.
*
* @return
*/
public static String getKMLCommaDelimitedString(GisLocation GisLocation)
{
return GisLocation.getLongitude() + "," + GisLocation.getLatitude() + "," + GisLocation.getAltitude();
}
/**
* @param that
* @return positive if this is farther north than that, negative if that is more north; 0 if they
* lie on exactly the same parallel.
*/
public static double compareNS(GisLocation GisLocation, GisLocation that)
{
return GisLocation.getLatitude() - that.getLatitude();
}
/**
* @param that
* @return compares two GPSDatum's based on the acute angle between their longitudes. Returns 1 if
* this is farther east than that, -1 if this is farther west, 0 if the two points lie on
* the same arc, 180/-180 if they are opposite.
*/
public static double compareEW(GisLocation GisLocation, GisLocation that)
{
double diff = GisLocation.getLongitude() - that.getLongitude();
if (diff > 180)
{
return diff - 360;
}
else if (diff < -180)
{
return diff + 360;
}
else
{
return diff;
}
}
/**
* Uses the haversine formula to compute the great-circle direct distance from this to the other
* point. Does not take into account altitude.
*
* Result is given in meters.
*
* Formula used from http://www.movable-type.co.uk/scripts/latlong.html.
*
* @param other
* @return great-circle distance between this and other, in meters.
*/
public static double distanceTo(GisLocation GisLocation, GisLocation other)
{
return distanceTo(GisLocation, other.getLatitude(), other.getLongitude());
}
/**
* Uses the haversine formula to compute the great-circle direct distance from this to the other
* point. Does not take into account altitude.
*
* Result is given in meters.
*
* Formula used from http://www.movable-type.co.uk/scripts/latlong.html.
*
* @param otherLat
* @param otherLon
* @return great-circle distance between this and other, in meters.
*/
public static double distanceTo(GisLocation GisLocation, double otherLat, double otherLon)
{
double deltaLat = Math.toRadians(otherLat - GisLocation.getLatitude());
double deltaLon = Math.toRadians(otherLon - GisLocation.getLongitude());
double a = (Math.sin(deltaLat / 2.0) * Math.sin(deltaLat / 2.0))
+ (Math.cos(Math.toRadians(GisLocation.getLatitude())) * Math.cos(Math.toRadians(otherLat))
* Math.sin(deltaLon / 2.0) * Math.sin(deltaLon / 2.0));
double c = 2.0 * Math.atan2(Math.sqrt(a), Math.sqrt(1.0 - a));
return c * RADIUS_EARTH_METERS;
}
}