Обновить MapView из onLocationChanged () - PullRequest
       33

Обновить MapView из onLocationChanged ()

3 голосов
/ 13 сентября 2011

У меня проблема с прорисовкой маршрута при onLocationChanged ().

Итак, что я пытаюсь сделать, это: У меня есть пин-код (на основе carOverlayItem) на карте, а MyLocationOverlay показывает мою текущую позицию. Я хочу нарисовать маршрут между этими двумя точками. Таким образом, каждый раз, когда пользователь перемещается (мы получаем location и метод MyLocationOverlay.onLocationChanged () запущен), я выбираю координаты из Google в файле klm, анализирую его и заполняю массив объектами GeoPoint. После того, как я пытаюсь перебрать этот массив GeoPoint и добавить наложения с перезаписанным методом draw () в MapView

public class GMapMyLocationOverlay extends MyLocationOverlay {

    private MapView mapView;
    private CarOverlayItem carOverlayItem = null;
    private GeoPoint routeNodes[];

    public GMapMyLocationOverlay(Context context, MapView mapView, CarOverlayItem carOverlayItem) {
        super(context, mapView);
        this.mapView = mapView;
        this.carOverlayItem = carOverlayItem;
    }

    @Override
    public void onLocationChanged(Location location) {
        // redraw route to the car point
        if (!carOverlayItem.isEmpty()) {
            GeoPoint fromLocation = new GeoPoint((int)(location.getLatitude() * 1e6), (int)(location.getLongitude() * 1e6));

            GMapRouteHttpRequest pointsRequest = new GMapRouteHttpRequest(fromLocation, carOverlayItem.getOverlayItem().getPoint());
            routeNodes = pointsRequest.getRoutePoints();

            // if the point is not set to be on the road, google can return empty points array
            // in this case we will be drawing straight line between car position and current 
            // user's position on map
            if (routeNodes != null && routeNodes.length > 0) {
                for (int i = 1; i < routeNodes.length; i ++) {
                    mapView.getOverlays().add(new GMapRouteOverlay(routeNodes[i-1], routeNodes[i]));
                }
            }
        }
        super.onLocationChanged(location);
    }
}

А вот и мой класс GMapRouteOverlay

public class GMapRouteOverlay extends Overlay {

    private GeoPoint fromPoint;
    private GeoPoint toPoint;

    public GMapRouteOverlay(GeoPoint fromPoint, GeoPoint toPoint) {
        this.fromPoint = fromPoint;
        this.toPoint = toPoint;
    }

    @Override
    public void draw(Canvas canvas, MapView mapView, boolean shadow) {
        Projection projection = mapView.getProjection();

        Paint paint = new Paint();
        paint.setColor(Color.RED);
        paint.setStrokeWidth(5);
        paint.setAntiAlias(true);

        Point from = new Point();
        projection.toPixels(fromPoint, from);

        Point to = new Point();
        projection.toPixels(toPoint, to);

        Path path = new Path();
        path.moveTo(from.x, from.y);
        path.lineTo(to.x, to.y);
        canvas.drawPath(path, paint);
        super.draw(canvas, mapView, shadow);
    }
}

Я прочитал немного интернета и пришел к мысли, что мне нужно заполнить переменную routeNodes при onLocationChanged (), а затем вызвать mapView.invalidate (), чтобы нарисовать маршрут в методе MapView onDraw (), но столкнулся с проблемой, которую я я не знаю, как передать переменную routeNodes и намерения, это не вариант, как я понимаю.

Кроме того, возможно, MyLocationOverlay с методом onLocationChanged () работают не в потоке пользовательского интерфейса, и поэтому я не могу рисовать на карте, но в этом случае, я думаю, я должен получить ошибку, которая не брошен. Я запутался и могу найти любое решение.

Любая помощь будет оценена.

Спасибо.

Ответы [ 3 ]

2 голосов
/ 25 ноября 2012

Будьте осторожны при использовании сетевых данных в потоке пользовательского интерфейса, это не работает в Android 4.0 и выше.

Вам нужно использовать AsyncTask

1 голос
/ 14 сентября 2011

На самом деле, моя версия тоже работает, я заметил, что Google возвращает долготу сначала и только потом широту, поэтому у меня возникла проблема из-за путаницы с параметрами при разборе файла klm. Так что +1 для меня тоже =)

0 голосов
/ 13 сентября 2011

вы можете обновить отображение карты, вызвав статический метод класса (этот класс был расширен с помощью MapActivity) следующим образом.

@Override
public void onLocationChanged(Location location) {
   super.onLocationChanged(location);
   MyMapClass.updateLocation(location);
}

и в вашем классе сделайте так.

class MyMapClass extends MapActivity{
   private static MapView mapview;
   public void onCreate(){} //// your oncreate() method

   public static void updateLocation(Location location){
         // here you can get the location value using this location object now pass this value to draw the location or your current location
        // and then call mapview.invalidate()
   }
}
...