基于纬度在谷歌地图上绘制路径
Posted
技术标签:
【中文标题】基于纬度在谷歌地图上绘制路径【英文标题】:Draw path on google map based on lat lang 【发布时间】:2016-09-05 08:10:11 【问题描述】:我想在谷歌地图上绘制路径。
基本上我在特定时间间隔后跟踪用户位置。当用户到达某个目的地时,我需要绘制他到达该目的地所遵循的路径。
它工作正常,但问题是它显示的是锯齿形路径。见下图。
我想要什么:
我想绘制一条正确的路径,然后是我在跟踪过程中得到的点。
我的尝试
我搜索并找到了this 链接,在该链接中我们最多可以传递 8 个点来获取方向。这是谷歌地图的非商业用户允许的最大限制。有没有其他方法可以实现这一点。因为我有很多点要在地图上画。
绘制折线的代码
private void drawPath()
if (mMap != null)
mMap.clear();
int count = 0;
LatLng prev = null;
String[] mProjection = LocTable.COLUMN_ID, LocTable.COLUMN_LONGITUDE, LocTable.COLUMN_LATITUDE;
String mSelectionClause = LocTable.COLUMN_ID + "> ?";
String[] mSelectionArgs = "0";
String mSortOrder = LocTable.COLUMN_ID;
Cursor mCursor = getContentResolver().query(
LocContentProvider.CONTENT_URI, // The content URI of the words table
mProjection, // The columns to return for each row
mSelectionClause, // Selection criteria
mSelectionArgs, // Selection criteria
mSortOrder);
if(mCursor != null && mCursor.getCount()!=0)
Log.i("cursor", "Count: " + mCursor.getCount() + "|Column count: " + mCursor.getColumnCount());
if (mCursor.moveToFirst())
do
if (mMap != null)
float lon = mCursor.getFloat(1);
float lat = mCursor.getFloat(2);
LatLng current = new LatLng(lat, lon);
markerPoints.add(current);
if (count == 0)
prev = current;
CameraUpdate cameraUpdate = CameraUpdateFactory.newLatLngZoom(current, 19);
mMap.animateCamera(cameraUpdate);
mMap.addPolyline((new PolylineOptions())
.add(prev, current).width(6).color(Color.BLUE)
.visible(true));
prev=current;
count++;
while (mCursor.moveToNext());
mCursor.close();
感谢您的帮助。
【问题讨论】:
我认为您必须在步行或开车时绘制路径? 并发布您的尝试或代码 画一条折线。您可以将点列表(latlng)传递给折线,然后将其添加到您的地图developers.google.com/android/reference/com/google/android/gms/… @Ravi 我需要绘制两种类型的路径......在代码中我只是在保存在本地数据库中的谷歌上绘制折线 @PedroOliveira 我已添加代码,请检查。我在这里做错了什么。 【参考方案1】:我同意antonio 的回答。问题不在于您的绘图功能。您只需绘制路径,无论设备为您提供位置。问题是您的设备没有提供准确的位置。
让我简要介绍一下位置功能。
设备中有三种提供位置的提供者。
1 个 GPS 提供商。
此提供商使用卫星确定位置。根据条件,此提供程序可能需要一段时间才能返回位置修复。需要权限 ACCESS_FINE_LOCATION。
GPS 位置提供程序的 extras Bundle 可以包含以下键/值对:
satellites - 用于获得修复的卫星数量
2 网络提供商。
此提供商根据手机信号塔和 WiFi 接入点的可用性确定位置。通过网络查找检索结果。
3 被动提供者。
当其他应用程序或服务请求位置更新时,此提供程序可用于被动接收位置更新,而无需您自己实际请求位置。该提供者将返回由其他提供者生成的位置。您可以查询 getProvider() 方法来确定位置更新的来源。需要权限 ACCESS_FINE_LOCATION,但如果未启用 GPS,此提供程序可能只会返回粗略的修复。
参考:
Android Location Manager
Android Location Providers - GPS or Network Provider?
根据我的经验,我可以说
GPS Provider
给了你准确的信息 位置与Network Provider
相比,但需要开放环境,GPS provider
没有给出建筑物内部的准确位置。
getAccuracy().
返回一个描述此提供程序的水平精度的常量。如果提供者返回更精细或精确的位置,则返回ACCURACY_FINE
,否则如果位置只是近似值,则返回ACCURACY_COARSE
。
当位置从 GPS 提供者更改时,此方法将返回精确值,否则将返回近似值或 0 值。
参考:Location.getAccuracy()
解决方案:
仅使用 GPS 提供程序
Find out your location is accurate or not.
推荐使用谷歌客户端 Sample Example.
【讨论】:
【参考方案2】:问题不在于您的绘图功能,而在于您使用接收到的位置获取路径点的方法。
您需要考虑两个因素:
首先,接收位置的准确性。您可以使用Location.getAccuracy()
方法(documentation)获得准确度。精度以米为单位,因此越低越好。
另一方面,只有当您的新位置与您上次添加的位置之间的距离超过给定距离时,您才可能希望将新位置添加到折线中。
结合这两种考虑的示例:
private static final float MINIMUM_ACCURACY = 10; // If the accuracy of the measurement is worse than 10 meters, we will not take the location into account
private static final float MINIMUM_DISTANCE_BETWEEN_POINTS = 20; // If the user hasn't moved at least 20 meters, we will not take the location into account
private Location lastLocationloc;
// ...
public void onLocationChanged(Location mylocation)
if (mylocation.getAccuracy() < MINIMUM_ACCURACY)
if (lastLocationloc == null || lastLocationloc.distanceTo(mylocation) > MINIMUM_DISTANCE_BETWEEN_POINTS)
// Add the new location to your polyline
lastLocationloc = mylocation;
【讨论】:
【参考方案3】:您是否查看过新的Roads Api?它将计算精度并返回最合理的值来绘制线。它还提供了当前道路的速度限制。
【讨论】:
【参考方案4】:添加到@antonio 答案。您可以按如下方式指定优先级和位移。这将确保您可以获得尽可能高的准确性
private int mInterval =5;
private static final long MIN_DISTANCE_CHANGE_FOR_UPDATES = 10;
private static final float MIN_ACCURACY = 10;
private Location lastKnownLocation;
@Override
public void onConnected(Bundle bundle)
locationRequest = LocationRequest.create();
locationRequest.setInterval(mInterval * 1000); // milliseconds
locationRequest.setFastestInterval(mInterval * 1000);
locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
locationRequest.setSmallestDisplacement(MIN_DISTANCE_CHANGE_FOR_UPDATES);//distance change
int permissionCheck = ContextCompat.checkSelfPermission(appContext, Manifest.permission.ACCESS_COARSE_LOCATION);
if (permissionCheck!= PackageManager.PERMISSION_DENIED)
LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient,
locationRequest, this);
现在在 onLocationChanged 方法中按照建议执行。
@Override
public void onLocationChanged(Location location)
if (location.getAccuracy() < MIN_ACCURACY )
if (lastKnownLocation == null || lastKnownLocation.distanceTo(location) > MIN_DISTANCE_CHANGE_FOR_UPDATES)
lastKnownLocation = location;
注意:
虽然从 NetworkProvider 检索位置更快,但 如果设备是静态的,则在特定时间间隔内接收到的位置 变化。上述逻辑将使我们有机会避免 不相关的值并跟踪/处理有效值。
Fused Location Provider Api Details
【讨论】:
以上是关于基于纬度在谷歌地图上绘制路径的主要内容,如果未能解决你的问题,请参考以下文章