我正在使用app并尝试获取用户所经历的速度和距离。我已经使用Google Play服务定位类来获得速度,但它总是返回0.0值,而且根本不可靠。我想要实时准确的速度和距离。
我已经在我的设备上安装了GPS车速表应用程序,它非常完美,即使我走路也会给我速度。我想得到同样的东西。我对如何获得速度,使用位置或使用加速度计感到困惑,还是有其他方法可以做到这一点?
我的代码可在此链接上找到: -
Drawing route on Google Maps using Google Maps Android API v2
我正在开发基于纯位置的应用程序,其中包括地图,速度以及与地点相关的其他相关内容。
如果有任何人有任何想法,请帮助我解决速度和距离问题。
答案 0 :(得分:13)
我必须处理同样的问题,你可以做的是使用Location Strategies代码。
然后,在每次更新位置时,您可以节省当前更新的时间。因此,您将拥有上一个和当前位置以及更新时间。
然后计算这两个位置(新旧位置)之间的距离(以米为单位)
private static long calculateDistance(double lat1, double lng1, double lat2, double lng2) {
double dLat = Math.toRadians(lat2 - lat1);
double dLon = Math.toRadians(lng2 - lng1);
double a = Math.sin(dLat / 2) * Math.sin(dLat / 2)
+ Math.cos(Math.toRadians(lat1))
* Math.cos(Math.toRadians(lat2)) * Math.sin(dLon / 2)
* Math.sin(dLon / 2);
double c = 2 * Math.asin(Math.sqrt(a));
long distanceInMeters = Math.round(6371000 * c);
return distanceInMeters;
}
那么,你有距离和时差,我认为获得速度并不是什么大问题。
答案 1 :(得分:1)
当我使用Google Play Location API时,我也遇到了这个问题,我希望这可以提供帮助。
它返回0,因为您的设备无法锁定GPS,或无法连接到GPS。
我尝试使用较旧的lenovo设备获得速度,并且它返回0,因为它无法锁定gps。
我尝试使用三星Galaxy nexus并且它恢复了我的速度(有更好的GPS传感器)。
手机中的GPS传感器可能不太好,或者您所在的GPS信号较弱的区域(如房屋或建筑物内)。
如果location.hasSpeed为false,我所做的是计算速度,如果location.hasSpeed为true,则使用location.getSpeed。
我还尝试使用活动识别在计算时具有更好的速度准确度。
//Computation for speed
cur_time = System.currentTimeMillis() / 1000L;
if (location.hasSpeed()) {
loc_Speed = location.getSpeed();
//counter goes back to 0
count_OnFoot = 0;
Toast.makeText(getBaseContext(), "has speed", Toast.LENGTH_SHORT).show();
} else {
float[] result = new float[1];
location.distanceBetween(prev_latitude, prev_longitude,
loc_Latitude, loc_Longitude,
result);
float loc_distance = result[0];
//speed if location.getSpeed is null
loc_Speed = loc_distance/(cur_time - prev_time);
//if activity type is on foot
//estimate AVE_RUNNING_SPEED = 3m/s
if (act_ActivityType.equals(ActivityRecognitionService.ACT_ON_FOOT) && loc_Speed > AVE_RUNNING_SPEED) {
count_OnFoot++;
if (count_OnFoot < 2) {
Toast.makeText(getBaseContext(), "on foot and 1st > 3m/s", Toast.LENGTH_SHORT).show();
/*
* Since the speed is more than
* the average running speed,we will
* assume that its not a correct value
* and a fault that it detected a very far signal from the previous one.
* (This happens sometimes)
* We will assign the previous speed
* as its current speed.
*/
loc_Speed = prev_Speed;
} else {
Toast.makeText(getBaseContext(), "on foot and TWICE > 3m/s in a row", Toast.LENGTH_SHORT).show();
/*
* Do Nothing
* loc_Speed is equals the computed speed
* if it happens twice or more in a row.
* We will assume that its running fast.
*/
}
}else {
count_OnFoot = 0;
}
}
prev_Speed = loc_Speed;
/*
* If more than 60% sure that its still.
*
* Let your speed and direction be 0
* latitude and longitude should not change
*/
if (act_ActivityType.equals(ActivityRecognitionService.ACT_STILL)) {
loc_Speed = 0;
loc_Direction = 0;
if (prev_latitude != 0 && prev_longitude != 0) {
loc_Latitude = prev_latitude;
loc_Longitude = prev_longitude;
}
}
prev_time = cur_time;
prev_latitude = loc_Latitude;
prev_longitude = loc_Longitude;
//Note: My activity type will return on foot or still if its more than 60% sure
//otherwise null.
答案 2 :(得分:1)
在这个答案中,我将向您展示获得当前速度的两个主要途径。一个是通过使用位置服务(location.getSpeed())而另一个是旧学校手动计算速度版本。
首先定义三个主要的全局变量
double curTime= 0;
double oldLat = 0.0;
double oldLon = 0.0;
现在转到 onLocationChannged 方法,然后在其中调用此方法,
getspeed(location);
现在让我们实现 getSpeed 方法
private void getspeed(Location location){
double newTime= System.currentTimeMillis();
double newLat = location.getLatitude();
double newLon = location.getLongitude();
if(location.hasSpeed()){
float speed = location.getSpeed();
Toast.makeText(getApplication(),"SPEED : "+String.valueOf(speed)+"m/s",Toast.LENGTH_SHORT).show();
} else {
double distance = calculationBydistance(newLat,newLon,oldLat,oldLon);
double timeDifferent = newTime - curTime;
double speed = distance/timeDifferent;
curTime = newTime;
oldLat = newLat;
oldLon = newLon;
Toast.makeText(getApplication(),"SPEED 2 : "+String.valueOf(speed)+"m/s",Toast.LENGTH_SHORT).show();
}
}
好的,我们完成了它,现在实现 calculationBydistance 方法
public double calculationBydistance(double lat1, double lon1, double lat2, double lon2){
double radius = EARTH_RADIUS;
double dLat = Math.toRadians(lat2-lat1);
double dLon = Math.toRadians(lon2-lon1);
double a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(Math.toRadians(lat1)) * Math.cos(Math.toRadians(lat2)) *
Math.sin(dLon/2) * Math.sin(dLon/2);
double c = 2 * Math.asin(Math.sqrt(a));
return radius * c;
}
在这里其他部分,速度将以m /毫秒为单位,您可以将其转换为秒......我们已经完成了
答案 3 :(得分:1)
public static double getSpeed(Location currentLocation, Location oldLocation)
{
double newLat = currentLocation.getLatitude();
double newLon = currentLocation.getLongitude();
double oldLat = oldLocation.getLatitude();
double oldLon = oldLocation.getLongitude();
if(currentLocation.hasSpeed()){
return currentLocation.getSpeed();
} else {
double radius = 6371000;
double dLat = Math.toRadians(newLat-oldLat);
double dLon = Math.toRadians(newLon-oldLon);
double a = Math.sin(dLat/2) * Math.sin(dLat/2) +
Math.cos(Math.toRadians(newLat)) * Math.cos(Math.toRadians(oldLat)) *
Math.sin(dLon/2) * Math.sin(dLon/2);
double c = 2 * Math.asin(Math.sqrt(a));
double distance = Math.round(radius * c);
double timeDifferent = currentLocation.getTime() - oldLocation.getTime();
return distance/timeDifferent;
}
}