(Location) Implement horizontal and vertical accuracy - Android's

location API only provides horizontal API but iOS/OSX API supports
both horizontal and vertical. Maybe consider implementing vertical
accuracy for Android by hand later
This commit is contained in:
twinaphex 2013-12-19 17:36:27 +01:00
parent 2f1327bf3e
commit da6e360e49
6 changed files with 52 additions and 28 deletions

View File

@ -215,11 +215,13 @@ LocationListener
}
/*
* Gets the accuracy of the current location in meters.
* Gets the horizontal accuracy of the current location
* in meters. (NOTE: There seems to be no vertical accuracy
* for a given location with the Android location API)
*
* @return the accuracy of the current position.
* @return the horizontal accuracy of the current position.
*/
public float onLocationGetAccuracy()
public float onLocationGetHorizontalAccuracy()
{
return mCurrentLocation.getAccuracy();
}

View File

@ -26,6 +26,8 @@ static CLLocationManager *locationManager;
static bool locationChanged;
static CLLocationDegrees currentLatitude;
static CLLocationDegrees currentLongitude;
sttaic CLLocationAccuracy currentHorizontalAccuracy;
sttaic CLLocationAccuracy currentVerticalAccuracy;
// Define compatibility symbols and categories
#ifdef IOS
@ -364,10 +366,14 @@ didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer
return currentLongitude;
}
- (double)onLocationGetAccuracy
- (double)onLocationGetHorizontalAccuracy
{
/* TODO/FIXME - implement */
return 0.0;
return currentHorizontalAccuracy;
}
- (double)onLocationGetVerticalAccuracy
{
return currentVerticalAccuracy;
}
- (bool)onLocationHasChanged
@ -383,14 +389,19 @@ didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer
locationChanged = true;
currentLatitude = newLocation.coordinate.latitude;
currentLongitude = newLocation.coordinate.longitude;
currentHorizontalAccuracy = newLocation.horizontalAccuracy;
currentVerticalAccuracy = newLocation.verticalAccuracy;
RARCH_LOG("didUpdateToLocation - latitude %f, longitude %f\n", (float)currentLatitude, (float)currentLongitude);
}
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
{
locationChanged = true;
currentLatitude = [[locations objectAtIndex:([locations count]-1)] coordinate].latitude;
currentLongitude = [[locations objectAtIndex:([locations count]-1)] coordinate].longitude;
CLLocation *location = [locations objectAtIndex:([locations count]-1)];
currentLatitude = [location coordinate].latitude;
currentLongitude = [location coordinate].longitude;
currentHorizontalAccuracy = [location horizontalAccuracy];
currentVerticalAccuracy = [location verticalAccuracy];
RARCH_LOG("didUpdateLocations - latitude %f, longitude %f\n", (float)currentLatitude, (float)currentLongitude);
}
@ -761,7 +772,8 @@ static void apple_location_stop(void *data)
[[RAGameView get] onLocationStop];
}
static bool apple_location_get_position(void *data, double *lat, double *lon, double *accuracy)
static bool apple_location_get_position(void *data, double *lat, double *lon, double *horiz_accuracy,
double *vert_accuracy)
{
(void)data;
@ -772,13 +784,15 @@ static bool apple_location_get_position(void *data, double *lat, double *lon, do
*lat = [[RAGameView get] onLocationGetLatitude];
*lon = [[RAGameView get] onLocationGetLongitude];
*accuracy = [[RAGameView get] onLocationGetAccuracy];
*horiz_accuracy = [[RAGameView get] onLocationGetHorizontalAccuracy];
*vert_accuracy = [[RAGameView get] onLocationGetVerticalAccuracy];
return true;
fail:
*lat = 0.0;
*lon = 0.0;
*accuracy = 0.0;
*lat = 0.0;
*lon = 0.0;
*horiz_accuracy = 0.0;
*vert_accuracy = 0.0;
return false;
}

View File

@ -648,14 +648,16 @@ void driver_location_set_interval(unsigned interval_msecs, unsigned interval_dis
driver.location->set_interval(driver.location_data, interval_msecs, interval_distance);
}
bool driver_location_get_position(double *lat, double *lon, double *accuracy)
bool driver_location_get_position(double *lat, double *lon, double *horiz_accuracy,
double *vert_accuracy)
{
if (driver.location && driver.location_data)
return driver.location->get_position(driver.location_data, lat, lon, accuracy);
return driver.location->get_position(driver.location_data, lat, lon, horiz_accuracy, vert_accuracy);
*lat = 0.0;
*lon = 0.0;
*accuracy = 0.0;
*horiz_accuracy = 0.0;
*vert_accuracy = 0.0;
return false;
}
#endif

View File

@ -375,7 +375,7 @@ typedef struct location_driver
bool (*start)(void *data);
void (*stop)(void *data);
bool (*get_position)(void *data, double *lat, double *lon, double *accuracy);
bool (*get_position)(void *data, double *lat, double *lon, double *horiz_accuracy, double *vert_accuracy);
void (*set_interval)(void *data, unsigned interval_msecs, unsigned interval_distance);
const char *ident;
} location_driver_t;
@ -603,7 +603,7 @@ void driver_camera_poll(void);
#ifdef HAVE_LOCATION
bool driver_location_start(void);
void driver_location_stop(void);
bool driver_location_get_position(double *lat, double *lon, double *accuracy);
bool driver_location_get_position(double *lat, double *lon, double *horiz_accuracy, double *vert_accuracy);
void driver_location_set_interval(unsigned interval_msecs, unsigned interval_distance);
#endif

View File

@ -766,7 +766,8 @@ typedef void (*retro_location_stop_t)(void);
// Get the position of the current location. Will set parameters to 0 if no new
// location update has happened since the last time.
typedef bool (*retro_location_get_position_t)(double *lat, double *lon, double *accuracy);
typedef bool (*retro_location_get_position_t)(double *lat, double *lon, double *horiz_accuracy,
double *vert_accuracy);
struct retro_location_callback
{

View File

@ -26,7 +26,7 @@ typedef struct android_location
jmethodID onLocationSetInterval;
jmethodID onLocationGetLongitude;
jmethodID onLocationGetLatitude;
jmethodID onLocationGetAccuracy;
jmethodID onLocationGetHorizontalAccuracy;
jmethodID onLocationHasChanged;
} androidlocation_t;
@ -72,8 +72,8 @@ static void *android_location_init(void)
if (!androidlocation->onLocationGetLongitude)
goto dealloc;
GET_METHOD_ID(env, androidlocation->onLocationGetAccuracy, class, "onLocationGetAccuracy", "()F");
if (!androidlocation->onLocationGetAccuracy)
GET_METHOD_ID(env, androidlocation->onLocationGetHorizontalAccuracy, class, "onLocationGetHorizontalAccuracy", "()F");
if (!androidlocation->onLocationGetHorizontalAccuracy)
goto dealloc;
GET_METHOD_ID(env, androidlocation->onLocationGetLongitude, class, "onLocationSetInterval", "(II)V");
@ -129,7 +129,8 @@ static void android_location_stop(void *data)
CALL_VOID_METHOD(env, android_app->activity->clazz, androidlocation->onLocationStop);
}
static bool android_location_get_position(void *data, double *latitude, double *longitude, double *accuracy)
static bool android_location_get_position(void *data, double *latitude, double *longitude, double *horiz_accuracy,
double *vert_accuracy)
{
struct android_app *android_app = (struct android_app*)g_android;
androidlocation_t *androidlocation = (androidlocation_t*)data;
@ -137,7 +138,7 @@ static bool android_location_get_position(void *data, double *latitude, double *
if (!env)
goto fail;
jdouble lat, lon, accuhurtz;
jdouble lat, lon, horiz_accu;
jboolean newLocation;
CALL_BOOLEAN_METHOD(env, newLocation, android_app->activity->clazz, androidlocation->onLocationHasChanged);
@ -147,21 +148,25 @@ static bool android_location_get_position(void *data, double *latitude, double *
CALL_DOUBLE_METHOD(env, lat, android_app->activity->clazz, androidlocation->onLocationGetLatitude);
CALL_DOUBLE_METHOD(env, lon, android_app->activity->clazz, androidlocation->onLocationGetLongitude);
CALL_DOUBLE_METHOD(env, accuhurtz, android_app->activity->clazz, androidlocation->onLocationGetAccuracy);
CALL_DOUBLE_METHOD(env, horiz_accu, android_app->activity->clazz, androidlocation->onLocationGetHorizontalAccuracy);
if (lat != 0.0)
*latitude = lat;
if (lon != 0.0)
*longitude = lon;
if (accuhurtz != 0.0)
*accuracy = accuhurtz;
if (horiz_accu != 0.0)
*horiz_accuracy = horiz_accu;
/* TODO/FIXME - custom implement vertical accuracy since Android location API does not have it? */
*vert_accuracy = 0.0;
return true;
fail:
*latitude = 0.0;
*longitude = 0.0;
*accuracy = 0.0;
*horiz_accuracy = 0.0;
*vert_accuracy = 0.0;
return false;
}