3

I have an issue drawing a route when onLocationChanged().

So what I'm trying to do is: I have a pin (based on carOverlayItem) on the map and MyLocationOverlay showing my current position. I want to draw a route between those two points. So, each time when user moves (we receive location and MyLocationOverlay.onLocationChanged() method is triggered), I'm fetching coordinates from Google in klm file, parsing it and filling an array with GeoPoint objects. After I'm trying to iterate through that GeoPoint array and add Overlays with Overwritten draw() method to 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);
    }
}

And here is my GMapRouteOverlay class

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);
    }
}

I've read some internet and came up with idea that I need to fill routeNodes variable when onLocationChanged() and then call mapView.invalidate() to draw a route in onDraw() MapView method, but faced an issue that I don't know how to transfer routeNodes variable and intents is not an option here as I understand.

Also, may be, that MyLocationOverlay with onLocationChanged() method are running in not UI thread and that is why I can't draw on the map, but in this case, I think, I should get an error, which is not thrown. I'm confused and can find any solution.

Any help would be appreciated.

Thanks.

Dmitry
  • 227
  • 3
  • 12

3 Answers3

2

Be careful when consuming Network data on UI thread, this doesn't work in android 4.0 and above.

You need to use AsyncTask

  • 1
    Welcome to SO! A little more explanation and an example would make this an even better answer, I think :-) – poplitea Nov 25 '12 at 19:57
1

Actually, my version is working too, I noticed that Google returns longitude first and only then latitude, so I had problem because of mess with parameters while parsing klm file. So +1 for me too =)

Dmitry
  • 227
  • 3
  • 12
0

you can update the mapview by calling the static method of class(this class was extends by MapActivity) like this way.

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

and in the your class do this way.

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()
   }
}
Pratik
  • 30,639
  • 18
  • 84
  • 159