Android: How to measure distance with gps - android

I am trying to make a application,which is take latitude and longitude on current place of the user. And count momentary,what distance is travel the user in km.
The "currentLat" and "currentLon" is current latitude and longitude of the user.But I don't know what latitude and longitude to put for "endLat" and "ednLon".
Sorry for my bad english.
Thanks in advance.
///////////////////////////////////
I made it the app,but now have just one little problem.
When I started first time the program,I get value 5536 and when I restarted the program I get normal value 0.0
Again sorry for my bad english. :)
And guys thanks for helping me,you are the best :)
public class Gps extends Activity {
TextView display;
double currentLon=0 ;
double currentLat=0 ;
double lastLon = 0;
double lastLat = 0;
double distance;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
display = (TextView) findViewById(R.id.info);
LocationManager lm =(LocationManager) getSystemService(LOCATION_SERVICE);
lm.requestLocationUpdates(lm.GPS_PROVIDER, 0,0, Loclist);
Location loc = lm.getLastKnownLocation(lm.GPS_PROVIDER);
if(loc==null){
display.setText("No GPS location found");
}
else{
//set Current latitude and longitude
currentLon=loc.getLongitude();
currentLat=loc.getLatitude();
}
//Set the last latitude and longitude
lastLat=currentLat;
lastLon=currentLon ;
}
LocationListener Loclist = new LocationListener(){
#Override
public void onLocationChanged(Location location) {
// TODO Auto-generated method stub
//start location manager
LocationManager lm =(LocationManager) getSystemService(LOCATION_SERVICE);
//Get last location
Location loc = lm.getLastKnownLocation(lm.GPS_PROVIDER);
//Request new location
lm.requestLocationUpdates(lm.GPS_PROVIDER, 0,0, Loclist);
//Get new location
Location loc2 = lm.getLastKnownLocation(lm.GPS_PROVIDER);
//get the current lat and long
currentLat = loc.getLatitude();
currentLon = loc.getLongitude();
Location locationA = new Location("point A");
locationA.setLatitude(lastLat);
locationA.setLongitude(lastLon);
Location locationB = new Location("point B");
locationB.setLatitude(currentLat);
locationB.setLongitude(currentLon);
double distanceMeters = locationA.distanceTo(locationB);
double distanceKm = distanceMeters / 1000f;
display.setText(String.format("%.2f Km",distanceKm ));
}
#Override
public void onProviderDisabled(String provider) {
// TODO Auto-generated method stub
}
#Override
public void onProviderEnabled(String provider) {
// TODO Auto-generated method stub
}
#Override
public void onStatusChanged(String provider, int status, Bundle extras) {
// TODO Auto-generated method stub
}
};
}

Since you have two locations, why don't you consider using distanceTo:
float distanceMeters = location1.distanceTo(location2);
float distanceKm = distanceMeters / 1000f;

But I don't know what latitude and longitude to put for "endLat" and "ednLon".
endLat, endLon is a confusing name:
You should have lastLat, lastLon: the lat,lon received in the previous call of onGpsUpdate, save that into your e.g distanceCalculator.lastLat
where distanceCalculator is an object where you store that lastLat, and lastLon
Then you should have curLat, curLon: current lat, lon delivered in onGPSUpdate
Then calculate the distance from (lastLat, lastLon) -> (curLat, curLon),
and update your distanceCalculator.lastLat and lastLon.

Link
var R = 6371; // Radius of the earth in km
var dLat = (lat2-lat1).toRad(); // Javascript functions in radians
var dLon = (lon2-lon1).toRad();
var a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(lat1.toRad()) * Math.cos(lat2.toRad()) *
Math.sin(dLon/2) * Math.sin(dLon/2);
var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
var d = R * c; // Distance in km.

Related

Calculate Distance traveled android using location manager [duplicate]

This question already has answers here:
Android Calculate Distance Traveled
(2 answers)
Closed 6 years ago.
I am currently working on a simple fitness app that allows user to track his/her performance (running,walking). I have been using location manager to get the moving speed which works very fine. However I need to get the distance traveled, how can use location manager (long and lat) to get the distance ?
Thanks
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_track);
start = (Button) findViewById(R.id.btnStart);
speed = (TextView) findViewById(R.id.txtSpeed);
locationManager = (LocationManager) getSystemService(LOCATION_SERVICE);
//initialize location listener
locationListener = new LocationListener() {
#Override
public void onLocationChanged(Location location) {
getSpeed(location);
double lat2 = location.getLatitude();
double lng2 = location.getLongitude();
}
#Override
public void onStatusChanged(String s, int i, Bundle bundle) {
}
#Override
public void onProviderEnabled(String s) {
}
#Override
public void onProviderDisabled(String s) {
}
//get the speed from the given location updates
public void getSpeed(Location location) {
currentSpeed = (location.getSpeed() * 3600 / 1000);
String convertedSpeed = String.format("%.2f", currentSpeed);
speed.setText(convertedSpeed + "Km/h");
}
};
You can possibly find distance between each successive latitude and longitude and keep adding.
Here getting distance in kilometers (km)
private double distance(double lat1, double lon1, double lat2, double lon2) {
double theta = lon1 - lon2;
double dist = Math.sin(deg2rad(lat1))
* Math.sin(deg2rad(lat2))
+ Math.cos(deg2rad(lat1))
* Math.cos(deg2rad(lat2))
* Math.cos(deg2rad(theta));
dist = Math.acos(dist);
dist = rad2deg(dist);
dist = dist * 60 * 1.1515;
return (dist);
}
private double deg2rad(double deg) {
return (deg * Math.PI / 180.0);
}
private double rad2deg(double rad) {
return (rad * 180.0 / Math.PI);
}
Hope this helps you.

Tracking in Geofence radious

I have Created application for geo fence.
I implement location listener which sends me current Lat and Long.
I have array of Lat Long and i created Geofence from this array.
I want to check that Current lat long are within my Geofence Region or not?
Code For Geofence:-
private void createGeofence(double latitude, double longitude, int radius,
String geofenceType, String title) {
Marker stopMarker = googleMap.addMarker(new MarkerOptions()
.draggable(true)
.position(new LatLng(latitude, longitude))
.title(title)
);
googleMap.addCircle(new CircleOptions()
.center(new LatLng(latitude, longitude)).radius(radius)
.fillColor(Color.parseColor("#B2A9F6")));
}
Lat Long from Listener:-
#Override
public void onLocationChanged(Location location) {
// TODO Auto-generated method stub
Lat=location.getLatitude();
Lng=location.getLongitude();
Geocoder geocoder;
List<Address> addresses;
geocoder = new Geocoder(this, Locale.getDefault());
try {
addresses = geocoder.getFromLocation(Lat, Lng, 1);
address = addresses.get(0).getAddressLine(0);
city = addresses.get(0).getAddressLine(1);
country = addresses.get(0).getAddressLine(2);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
System.out.println("Lat Long is "+ Lat + " " + Lng);
}
Please help for this.
You could use the harvesine formula:
public static final double R = 6372.8; // In kilometers
public static double haversine(double lat1, double lon1, double lat2, double lon2) {
double dLat = Math.toRadians(lat2 - lat1);
double dLon = Math.toRadians(lon2 - lon1);
lat1 = Math.toRadians(lat1);
lat2 = Math.toRadians(lat2);
double a = Math.sin(dLat / 2) * Math.sin(dLat / 2) + Math.sin(dLon / 2) * Math.sin(dLon / 2) * Math.cos(lat1) * Math.cos(lat2);
double c = 2 * Math.asin(Math.sqrt(a));
return R * c;
}
That will give you the distance between the two locations. After that you could compare that distance with the geofence region radius to know if is inside the region.
Note: This distance will be in kilometers if your radius is on meters then just multiply the haversine method result with 1000 so that it's converted to meters.
Reference

method distanceTo(double) is undefined

I have a Problem to get the right way to get the distanceTo from my 2 Geo Points. How to get it work?
from the gps class:
double latitude; // latitude
String mlat;
latitude = location.getLatitude();
mlat = String.valueOf(latitude);
from the ListView:
// Get distance
String mReportA;
double mLocB;
int distance;
mReportA = e.getString("lat");
mReportA = e.getString("lon");
mLocB = gps.latitude;
mLocB = gps.longitude;
distance = mReportA.distanceTo(mLocB);
Error in Eclipse: The method distanceTo(double) is undefined for the type String
I get e.getString("lat"); from json
To calculate distance between two geopoint you can follow the below example.
double currentLatitude = location.getLatitude();
double currentLongitude = location.getLongitude();
double endLatitude = lat;
double endLongitude = lng;
float[] results = new float[3];
Location.distanceBetween(currentLatitude, currentLongitude,endLatitude, endLongitude, results);
BigDecimal bd = new BigDecimal(results[0]);// results in meters
BigDecimal rounded = bd.setScale(2, RoundingMode.HALF_UP);
double values = rounded.doubleValue();
EDIT
if (values > 1000) {
values = (Double) (values * 0.001f);// convert meters to Kilometers
bd = new BigDecimal(values);
rounded = bd.setScale(2, RoundingMode.HALF_UP);
values = rounded.doubleValue();
}
// Here is the code to find out the distance between two locations
float distance;
Location locationA = new Location("A");
locationA.setLatitude(latA);
locationA.setLongitude(lngA);
Location locationB = new Location("B");
locationB.setLatitude(latB);
LocationB.setLongitude(lngB);
distance = locationA.distanceTo(locationB);

Convert latitude and longitude into esri arcGIS MapPoint

I am having trouble in converting the latitude and longitude values into android esri arcGIS map Point. Here's my code to get latitude and longitude values from GPS coordinates:
LocationManager lm;
String towers;
double lat;
double longi;
TextView txt;
lm = (LocationManager) getSystemService(Context.LOCATION_SERVICE);
Criteria crit = new Criteria();
towers = lm.getBestProvider(crit, false);
Location location = lm.getLastKnownLocation(towers);
if(location != null)
{
lat = location.getLatitude();
longi = location.getLongitude();
}
now I have the latitude and longitude values. Now all I need is to convert these values into valid esri arcGIS MapPoint. Can anyone help me?
Thanks in advance.
Assuming you're using the ESRI Android API? If so, create a graphics layer on your map. Then create a point object
com.esri.core.geometry.Point
Point myPoint = new Point();
then set the x/y values:
myPoint.setX(longi);
myPoint.setY(lat);
then add myPoint to the graphics object.
http://help.arcgis.com/en/arcgismobile/10.0/apis/android/api/index.html
Yes, it is possible. But you don't use the locationmanager in ArcGis.
ArcGIS has the predefined method like LocationListener, that is: OnStatusChangedListener.
See the below code for converting location latitude and longitude into esri arcGIS MapPoint.
mMapView.setOnStatusChangedListener(new OnStatusChangedListener() {
/**
*
*/
private static final long serialVersionUID = 1L;
public void onStatusChanged(Object source, STATUS status) {
if (source == mMapView && status == STATUS.INITIALIZED) {
LocationService ls = mMapView.getLocationService();
ls.setAutoPan(false);
ls.setLocationListener(new LocationListener() {
boolean locationChanged = false;
// Zooms to the current location when first GPS fix
// arrives.
public void onLocationChanged(Location loc) {
if (!locationChanged) {
locationChanged = true;
double locy = loc.getLatitude();
double locx = loc.getLongitude();
Point wgspoint = new Point(locx, locy);
Point mapPoint = (Point) GeometryEngine.project(wgspoint,
SpatialReference.create(4326),
mMapView.getSpatialReference());
Unit mapUnit = mMapView.getSpatialReference().getUnit();
double zoomWidth = Unit.convertUnits(
SEARCH_RADIUS, Unit.create(LinearUnit.Code.MILE_US), mapUnit);
Envelope zoomExtent = new Envelope(mapPoint, zoomWidth, zoomWidth);
mMapView.setExtent(zoomExtent);
GraphicsLayer gLayer = new GraphicsLayer();
PictureMarkerSymbol symbol = new
PictureMarkerSymbol(getResources().getDrawable(R.drawable.twiz_car_red));
Graphic graphic = new Graphic(mapPoint, symbol);
//Graphic point=new Graphic(new Point(x, y),new
SimpleMarkerSymbol(Color.CYAN,20,STYLE.CIRCLE));
gLayer.addGraphic(graphic);
mMapView .addLayer(gLayer);
}
}
public void onProviderDisabled(String arg0) {
}
public void onProviderEnabled(String arg0) {
}
public void onStatusChanged(String arg0, int arg1,
Bundle arg2) {
}
});
ls.start();
}
}
});
I've borrowed some code from here
private Point ToGeographic(Point pnt)
{
double mercatorX_lon = pnt.getX();
double mercatorY_lat = pnt.getY();
if (Math.abs(mercatorX_lon) < 180 && Math.abs(mercatorY_lat) < 90)
return pnt;
if ((Math.abs(mercatorX_lon) > 20037508.3427892) || (Math.abs(mercatorY_lat) > 20037508.3427892))
return pnt;
double x = mercatorX_lon;
double y = mercatorY_lat;
double num3 = x / 6378137.0;
double num4 = num3 * 57.295779513082323;
double num5 = Math.floor((double)((num4 + 180.0) / 360.0));
double num6 = num4 - (num5 * 360.0);
double num7 = 1.5707963267948966 - (2.0 * Math.atan(Math.exp((-1.0 * y) / 6378137.0)));
mercatorX_lon = num6;
mercatorY_lat = num7 * 57.295779513082323;
return new Point(mercatorX_lon, mercatorY_lat);
}
private Point ToWebMercator(Point pnt)
{
double mercatorX_lon = pnt.getX();
double mercatorY_lat = pnt.getY();
if ((Math.abs(mercatorX_lon) > 180 || Math.abs(mercatorY_lat) > 90))
return pnt;
double num = mercatorX_lon * 0.017453292519943295;
double x = 6378137.0 * num;
double a = mercatorY_lat * 0.017453292519943295;
mercatorX_lon = x;
mercatorY_lat = 3189068.5 * Math.log((1.0 + Math.sin(a)) / (1.0 - Math.sin(a)));
return new Point(mercatorX_lon, mercatorY_lat);
}
I make no claims of efficiency, but it's a starting point at least.
Disclaimer: I'm not an expert in this, but want to try to help. :)
There is now an ArcGIS Stack Exchange site. There's more information being added all the time and is a nice consolidated resource compared to what is out there disbursed on the interwebs.
For frameworks, I recommend GeoTools for Android.
As an aside, QGIS for Android is an interesting project from Marco Bernasocchi which you may find helpful as a reference.
Hope you can find what you're looking for!
i made a function that converts the two parameters of a location point to arcgis point :
private Point ConvertMyLocationPoint(final double x, final double y) {
Point wgspoint = new Point(x, y);
Point mapPoint = (Point) GeometryEngine.project(wgspoint, SpatialReference.create(4326),
mMapView.getSpatialReference());
return mapPoint;
}
//convert longitude and latitude to map point X Y
- (AGSPoint *)agsPointFromLatitude:(double)latitude longitude:(double)longitude
{
double mercatorX = longitude * 0.017453292519943295 * 6378137.0;
double a = latitude * 0.017453292519943295;
double mercatorY = 3189068.5 * log((1.0 + sin(a))/(1.0 - sin(a)));
AGSPoint *obj = [AGSPoint pointWithX:mercatorX y:mercatorY spatialReference: [AGSSpatialReference wgs84SpatialReference]];
return obj;
}

{Android App} How can I display distance from my current location and specified point?

i have researched this for hours and the only answers i see point me to
http://developer.android.com/reference/android/location/Location.html
and to use the Method
public static void distanceBetween (double startLatitude, double startLongitude, double endLatitude, double endLongitude, float[] results)
i need help understanding how this works in relation to my app. this is how i am retrieving my location.
LocationManager locationManager;
String context = Context.LOCATION_SERVICE;
locationManager = (LocationManager)getSystemService(context);
String provider = LocationManager.GPS_PROVIDER;
Location location = locationManager.getLastKnownLocation(provider);
updateWithNewLocation(location);
}
private void updateWithNewLocation(Location location) {
String latLongString;
TextView myLocationText;
myLocationText = (TextView)findViewById(R.id.myLocationText);
if (location != null) {
double lat = location.getLatitude();
double lng = location.getLongitude();
latLongString = "Lat:" + lat + "\nLong:" + lng;
} else {
latLongString = "No location found";
}
myLocationText.setText("Your Current Position is:\n" +
latLongString);
}
Can someone please help me out a little in understanding how to import my current location into this equation and then having the distance shown in my app?
thank you
public double calcdist()
{
int MILLION = 1000000;
int EARTH_RADIUS_KM = 6371;
double lat1 = la1 / MILLION;// latitude of location 1
double lon1 = lo1 / MILLION; //longitude of location 1
double lat2 = la2 / MILLION; //latitude of location 2
double lon2 = lo2 / MILLION;//longitude of location 2
double lat1Rad = Math.toRadians(lat1);
double lat2Rad = Math.toRadians(lat2);
double deltaLonRad = Math.toRadians(lon2 - lon1);
double dist = Math.acos(Math.sin(lat1Rad) * Math.sin(lat2Rad) + Math.cos(lat1Rad) * Math.cos(lat2Rad)
* Math.cos(deltaLonRad))
* EARTH_RADIUS_KM;
return dist;
}
You can use this code if you already got latitude and longitude of both the locations.
Create a location listener
Method isAccurateForUse is a custom method that simply checks accuracy of a location.
This should work:
public boolean locChanged = false;
public LocationManager locMgr = null;
public Location referenceL = null; // Your reference location
public Location currentKL = null; // Current known location
public Location currentLKL = null; // Current last known location
//Initialise the GPS listener
locMgr = (LocationManager) appCtx.getSystemService(Context.LOCATION_SERVICE);
locMgr.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, fixGpsListener);
currentLKL = locMgr.getLastKnownLocation(LocationManager.GPS_PROVIDER);
//Define the GPS listener
LocationListener fixGpsListener = new LocationListener()
{
public void onLocationChanged(Location location)
{
locChanged = true;
if (currentKL == null)
currentKL = location;
else if (isAccurateForUse())
{
currentLKL = currentKL;
currentKL = location;
updateDistance(meterToKilometer(currentKL.distanceTo(referenceL)));
}
}
public void onProviderDisabled(String provider)
{}
public void onProviderEnabled(String provider)
{}
public void onStatusChanged(String provider, int status, Bundle extras)
{}
};
currentKL.distanceTo(referenceL) >> gives the distance in meters
meterToKilometer >> converts meters to kilo-meters
updateDistance >> this method takes a string and updates a text-view that shows distance.
Cheers

Categories

Resources