Android如何在MapView中使用覆盖层自由绘制涂料?

5
在我的应用中,我想在地图视图上自由绘制图画,但是在搜索了很多信息后,最终通过在地图视图上绘制矩形形状得到了帮助。但我想要绘制自由手绘的锯齿形状,要如何修改我的代码呢?如果有任何帮助,请告诉我。
MapOverlay.java
  public class MapOverlay extends Overlay {

private float x1,y1,x2,y2;
private GeoPoint p1=null,p2=null;
private MapExampleActivity mv = null;
private Paint paint = new Paint();
private Path path = new Path();
private boolean isUp = false;

//constructor receiving the initial point
  public MapOverlay(MapExampleActivity mapV,float x,float y){
    paint.setStrokeWidth(2.0f);
    x1 = x;
    y1 = y;
    mv = mapV;
    p1 = mapV.getMapView().getProjection().fromPixels((int)x1,(int)y1);
}
//override draw method to add our custom drawings
@Override
public boolean draw(Canvas canvas, MapView mapView, boolean shadow, long when) {

    if(p1 != null && p2 != null){
        //get the 2 geopoints defining the area and transform them to pixels
        //this way if we move or zoom the map rectangle will follow accordingly
        Point screenPts1 = new Point();
        mapView.getProjection().toPixels(p1, screenPts1);
        Point screenPts2 = new Point();
        mapView.getProjection().toPixels(p2, screenPts2);                

        //draw inner rectangle
        paint.setColor(Color.BLUE);
     //   paint.setStyle(Style.FILL);
        canvas.drawPath(path, paint);       
        canvas.drawRect(screenPts1.x, screenPts1.y, screenPts2.x, screenPts2.y, paint);
        //draw outline rectangle

    //  paint.setColor(Color.YELLOW);
        paint.setStyle(Style.STROKE);
    //  canvas.drawRect(screenPts1.x, screenPts1.y, screenPts2.x, screenPts2.y, paint);
        canvas.drawPath(path, paint); 
    }
    return true;
}    

@Override
public boolean onTouchEvent(MotionEvent e, MapView mapView) {
    if(mv.isEditMode() && !isUp){

        if(e.getAction() == MotionEvent.ACTION_DOWN){
            x1 = y1 = 0;
            x1 = e.getX();
            y1 = e.getY();
            p1 = mapView.getProjection().fromPixels((int)x1,(int)y1);               
        }

        //here we constantly change geopoint p2 as we move out finger
        if(e.getAction() == MotionEvent.ACTION_MOVE){
            x2 = e.getX();
            y2 = e.getY();
            p2 = mapView.getProjection().fromPixels((int)x2,(int)y2);               
        }

        //---when user lifts his finger---
        if (e.getAction() == MotionEvent.ACTION_UP) {                
            isUp = true;
        }    
        return true;
    }
    return false;
}

使用此方法,我能够绘制矩形形状并且可以在再次单击切换按钮后进行绘制(可以多次绘制)。

矩形形状

我想要像下面的图像一样绘制线条(可以多次绘制)。

输入图像描述

最后我找到了这个链接,它提供了绘制矩形形状的方法:http://n3vrax.wordpress.com/2011/08/13/drawing-overlays-on-android-map-view/

只需将矩形更改为任意绘制,有什么建议吗?

1个回答

5
您可以使用下面的代码自由绘制一条线:

代码

public class HandDrawOverlay extends Overlay { 

private boolean editMode = false;
private boolean isTouched = false;
private Paint paint = new Paint(); 
private Point screenPt1 = new Point(); 
private Point screenPt2 = new Point(); 
private ArrayList<GeoPoint> points = null;

public HandDrawOverlay(){ 
    paint.setStrokeWidth(2.0f); 
    paint.setStyle(Style.STROKE); 
    paint.setColor(Color.BLUE); 
} 

@Override 
public void draw(Canvas canvas, MapView mapView, boolean shadow) {
    if(points != null && points.size() > 1){
        mapView.getProjection().toPixels(points.get(0), screenPt1); 
        for(int i=1; i<points.size();i++){
            mapView.getProjection().toPixels(points.get(i), screenPt2);
            canvas.drawLine(screenPt1.x, screenPt1.y, screenPt2.x, screenPt2.y, paint);
            screenPt1.set(screenPt2.x, screenPt2.y);
        }
    }
}     

@Override 
public boolean onTouchEvent(MotionEvent e, MapView mapView) { 
    if(editMode){ 
        int x = (int)e.getX();
        int y = (int)e.getY();
        GeoPoint geoP = mapView.getProjection().fromPixels(x,y);

        switch (e.getAction()) {
        case MotionEvent.ACTION_DOWN:
            isTouched = true;
            points = new ArrayList<GeoPoint>();
            points.add(geoP);
            break;
        case MotionEvent.ACTION_MOVE:
            if(isTouched)
                points.add(geoP);
            break;
        case MotionEvent.ACTION_UP:
            if(isTouched)
                points.add(geoP);
            isTouched = false;
            break;
        }
        mapView.invalidate();
        return true; 
    } 
    return false; 
}

/**
 * @return the editMode
 */
public boolean isEditMode() {
    return editMode;
}

/**
 * @param editMode the editMode to set
 */
public void setEditMode(boolean editMode) {
    this.editMode = editMode;
} 
}

使用

HandDrawOverlay handDrawOverlay;
handDrawOverlay = new HandDrawOverlay();
mapView.getOverlays().add(handDrawOverlay);

//Set edit mode to true to start drwaing
handDrawOverlay.setEditMode(true);

//Set edit mode to true to stop drwaing
handDrawOverlay.setEditMode(false);

注意

这是一个完整的示例,可以帮助您开始。但是,您应该优化代码使其更加高效(例如,在onDraw()中使用Path来存储绘图路径,在onTouch()中减少记录的点数等)。

享受吧。


我们使用一个绘制按钮在地图上进行绘画,当调用绘制按钮时,它会显示带有绘画的地图视图...然后我们会缩放和移动...但是从这个过程中,当第二次调用绘制按钮时也会绘制绘画。 - SubbaReddy PolamReddy
@Luic,第二次绘制时,第一次绘制的画面没有显示出来,当我点击按钮时无法缩放地图视图......只需查看示例链接,我们就能清楚地了解情况... - NagarjunaReddy
我无法理解你的评论,请重新表述。我可以向您保证,上面的代码完美运行,因为我在发布之前已经测试过了。关于缩放,当您在地图上绘制时,当然不能进行缩放。如果您想要缩放功能正常工作,您需要将 editMode() 设置为 false,或者将缩放按钮区域从绘制区域中排除。 - Luis
第一次绘制正常,但连续绘制时预览不显示。 - NagarjunaReddy
我编写的代码是用来绘制一条线的。你可以在MotionEvent.ACTION_DOWN时看到,我创建了一个新数组,丢弃了旧的数组。 - Luis

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接