Join FlipAndroid.COM Telegram Group: https://t.me/joinchat/F_aqThGkhwcLzmI49vKAiw


Dibuja un arco geográficamente preciso en un mapa para Android

Me gustaría dibujar un arco con un punto GPS central y dos puntos GPS finales. Puedo utilizar cualquier software de mapeo que se puede utilizar con android.

Hasta ahora he probado Google Maps para Android. Mapbox para Android. ARCGIS para android. Ninguno de ellos parece ser capaz de hacer esta tarea sencilla.

Supongo que necesito algún tipo de superposición.

Introduzca aquí la descripción de la imagen Introduzca aquí la descripción de la imagen

2 Solutions collect form web for “Dibuja un arco geográficamente preciso en un mapa para Android”

En primer lugar, tiene que cambiar la representación de geodatos.

De esto:

 36 ° 46'02.5 "S 174 ° 50'03.6" E GRC
 36 ° 56'18,3 "S 174 ° 33'09,7" E CWA 36 ° 52'19,2 "S 174 ° 29'23,5" E 5,0 'NM
 36 ° 48'19,8 "S 174 ° 25'37,7" E GRC
 36 ° 41'06,1 "S 174 ° 37'32,9" E CCA 36 ° 39'54,5 "S 174 ° 38'40,7" E 1,5 'NM
 36 ° 41'00,3 "S 174 ° 39'57,1" E GRC
 36 ° 39'49,4 "S 174 ° 41'32,3" E CCA 36 ° 38'43,5 "S 174 ° 40'15,7" E 1,5 'NM
 36 ° 39'17,5 "S 174 ° 41'59,7" E GRC
 36 ° 39'38,6 "S 174 ° 44'37,7" E GRC
 36 ° 37'08,8 "S 174 ° 47'27,4" E CWA 36 ° 42'03,8 "S 174 ° 46'17,0" E 5,0 'NM

A esto:

 -36.76736 174.83433 GRC
 -36.93842 174.55269 CWA -36.87200 174.48986 0.08333 NM
 -36.80550 174.42714 GRC
 -36,68503 174,62581 CCA -36,66514 174,64464 0,02500 NM
 -36.68342 174.66586 GRC
 -36,66372 174,69231 CCA -36,64542 174,67103 0,02500 NM
 -36.65486 174.69992 GRC
 -36.66072 174.74381 GRC
 -36.61911 174.79094 CWA -36.70106 174.77139 0.08333 NM

A continuación, puede utilizarlos para construir una ruta (por ejemplo, ruta SVG ):

<svg ...> <g transform="matrix(1250,0,0,1250,46206.909,-217995.49)" ...> <path d=" M -36.76736,174.83433 L -36.93842,174.55269 A 0.08333,0.08333 0 0,1 -36.80550,174.42714 L -36.68503,174.62581 A 0.02500,0.02500 0 0,0 -36.68342,174.66586 L -36.66372,174.69231 A 0.02500,0.02500 0 0,0 -36.65486,174.69992 L -36.66072,174.74381 L -36.61911,174.79094 A 0.08333,0.08333 0 0,1 -36.76736,174.83433 Z" .../> </g> </svg> 

Ejemplo SVG

En realidad, no hay API para crear curvas, arcos, etc. en GMaps / OSMDroid, por lo que debe dibujarlas como muchas líneas pequeñas. Significa hacer un poco de matemáticas, pero esta matemática puede ser hecha por la biblioteca de GeographicLib :

 @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); MapView map = (MapView) findViewById(R.id.map); map.setTileSource(TileSourceFactory.MAPNIK); map.setBuiltInZoomControls(true); map.setMultiTouchControls(true); IMapController mapController = map.getController(); mapController.setZoom(9); GeoPoint startPoint = new GeoPoint(-36.66372, 174.69231); mapController.setCenter(startPoint); Polygon polyline = new Polygon(this); List<GeoPoint> points = new LinkedList<>(); // I filled the data manually, but it can be done more clever, of course. GRC(points, new GeoPoint(-36.76736, 174.83433)); CWA(points, new GeoPoint(-36.93842, 174.55269), new GeoPoint(-36.87200, 174.48986), new GeoPoint(-36.80550, 174.42714), 0.08333); CCA(points, new GeoPoint(-36.68503, 174.62581), new GeoPoint(-36.66514, 174.64464), new GeoPoint(-36.68342, 174.66586), 0.02500); CCA(points, new GeoPoint(-36.66372, 174.69231), new GeoPoint(-36.64542, 174.67103), new GeoPoint(-36.65486, 174.69992), 0.02500); GRC(points, new GeoPoint(-36.66072, 174.74381)); CWA(points, new GeoPoint(-36.61911, 174.79094), new GeoPoint(-36.70106, 174.77139), new GeoPoint(-36.76736, 174.83433), //close shape going to the start point 0.08333); polyline.setPoints(points); polyline.setFillColor(0xA0FF00FF); polyline.setStrokeColor(Color.BLACK); polyline.setStrokeWidth(2f); map.getOverlays().add(polyline); map.invalidate(); } private void CCA(List<GeoPoint> points, GeoPoint startPoint, GeoPoint centerPoint, GeoPoint endPoint, double radius) { points.add(startPoint); GeodesicData f = Geodesic.WGS84.Inverse(centerPoint.getLatitude(), centerPoint.getLongitude(), startPoint.getLatitude(), startPoint.getLongitude()); GeodesicData t = Geodesic.WGS84.Inverse(centerPoint.getLatitude(), centerPoint.getLongitude(), endPoint.getLatitude(), endPoint.getLongitude()); double ffaz = f.azi1; double tfaz = t.azi1; final int decrement = 1; while (Math.abs((int)ffaz) != Math.abs((int)tfaz)) { GeodesicData llb = Geodesic.WGS84.Direct(centerPoint.getLatitude(), centerPoint.getLongitude(), ffaz, f.s12); points.add(new GeoPoint(llb.lat2, llb.lon2)); ffaz -= decrement; if (ffaz <0) { ffaz += 360; } } points.add(endPoint); } private void CWA(List<GeoPoint> points, GeoPoint startPoint, GeoPoint centerPoint, GeoPoint endPoint, double radius) { points.add(startPoint); GeodesicData f = Geodesic.WGS84.Inverse(centerPoint.getLatitude(), centerPoint.getLongitude(), startPoint.getLatitude(), startPoint.getLongitude()); GeodesicData t = Geodesic.WGS84.Inverse(centerPoint.getLatitude(), centerPoint.getLongitude(), endPoint.getLatitude(), endPoint.getLongitude()); double ffaz = f.azi1; double tfaz = t.azi1 > 0 ? t.azi1 : 360 + t.azi1; final int increment = 1; while (Math.abs((int)ffaz) != Math.abs((int)tfaz)) { GeodesicData llb = Geodesic.WGS84.Direct(centerPoint.getLatitude(), centerPoint.getLongitude(), ffaz, f.s12); points.add(new GeoPoint(llb.lat2, llb.lon2)); ffaz += increment; if (ffaz>360) { ffaz -= 360; } } points.add(endPoint); } private void GRC(List<GeoPoint> points, GeoPoint geoPoint) { points.add(geoPoint); } 

He utilizado osmdroid + OSMBonusPack, pero el código es bastante universal y se puede utilizar con Google Maps fácilmente.

El código fuente completo .

Resultado:

Osmdroid y OSMBonusPack juntos

Además, ¿te importaría decir qué tipo de geodatos publicaste? La forma en el mapa parece una zona de vuelo permitida, supongo.

Desafortunadamente, no puedo darte una respuesta completa ahora mismo, ya que esta pregunta requiere matemáticas pesadas y no puedo entender completamente los datos que has mostrado en la tabla. Supongo que usted está tratando de tener un resultado final que se parece a algo así. Si ese es el caso, tiene un punto central, un radio y el arco que comienza LatLng y termina LatLng (Esto también se puede calcular desde el punto central con matemáticas adicionales). Voy a tratar de actualizar esta respuesta si tengo la oportunidad de escribir algún código de manejo del lado de las matemáticas. Hasta donde yo sé, ninguna de las bibliotecas de mapas (Google Maps, Mapbox) incluye esto.

Básicamente, escribiría un método que devuelve un montón de puntos latlng siguiendo el arco que desea dibujar. De esto, dibujaría una línea usando el método de addPolyline .

 // Draw line from list of LatLng called pointsArray mapView.addPolyline(new PolylineOptions() .add(pointsArray) .color(Color.parseColor("#3bb2d0")) .width(2)); 

Espero que esto te ayude a salir, al menos con empezar y como he dicho, voy a tratar de añadir los bits de matemáticas más adelante si tengo la oportunidad.

    FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.