2012-05-28 63 views
2

我正在嘗試使用觸摸方法繪製一條線。如何在運行時在自定義視圖中繪製線條?

我希望當用戶觸摸一個特定點然後拖動手指時,該線應該被繪製。使用canvas.drawLine(_,_,_,_,_);不是畫線。因爲onDraw只能使用一次。

我的主要問題是 「如何繪製運行期間的線路,而無需使用onDraw()?」

編輯:

public class DrawView extends View { 
    int radius=30; 
    int initialX =0; 
    int initialY=0; 
    int finalX=0; 
    int finalY=0; 
    private Point currentPoint; 
    private int index; 
    static ArrayList<Point> pointListDrawView = new ArrayList<Point>(); 

    public DrawView(Context context, ArrayList<Point> pointList) { 
     super(context); 
     // TODO Auto-generated constructor stub 
     this.setBackgroundColor(Color.WHITE); 
     //pointListDrawView = pointList; 


     pointListDrawView.add(pt(600,200)); 

     pointListDrawView.add(pt(500,200)); 
     pointListDrawView.add(pt(400,200)); 
     pointListDrawView.add(pt(400,300)); 

     pointListDrawView.add(pt(400,400)); 
     pointListDrawView.add(pt(500,400)); 
     pointListDrawView.add(pt(400,400)); 

     pointListDrawView.add(pt(400,500)); 
     pointListDrawView.add(pt(400,600)); 
     pointListDrawView.add(pt(500,600)); 
     pointListDrawView.add(pt(600,600)); 

    } 
    private Point pt(int i, int j) { 
     // TODO Auto-generated method stub 
     Point P = new Point(i, j); 
     return P ; 
    } 
    Paint paint= new Paint(); 
    Canvas universalCanvas; 
    @Override 
    protected void onDraw(final Canvas canvas) { 

      paint.setColor(Color.GREEN); 
      paint.setStrokeWidth(10); 
      for(int i=0; i<pointListDrawView.size();i++){ 
      canvas.drawCircle(pointListDrawView.get(i).x, pointListDrawView.get(i).y, 15, paint); 
      } 
      universalCanvas = canvas; 
    //  drawLines(canvas); 
    } 

    @Override 
    public boolean onTouchEvent(MotionEvent event) { 
     // TODO Auto-generated method stub 

     int i =0; 

     switch (event.getAction()){ 

     case MotionEvent.ACTION_DOWN: 
       if(((event.getX()>pointListDrawView.get(i).x-radius) && (event.getX()<pointListDrawView.get(i).x+radius) && (event.getY()>pointListDrawView.get(i).y-radius) && (event.getY()<pointListDrawView.get(i).y+radius))) 

       { 
        Log.d("touch", "touched correct point"); 
        initialX=pointListDrawView.get(i).x; 
        initialY=pointListDrawView.get(i).y; 

       } 

       else{ 
        Log.d("touch", "touch discarded"); 
       return false; 
       } 
     break; 

     case MotionEvent.ACTION_MOVE: 
       universalCanvas.drawLine(initialX, initialY, event.getX(), event.getY(), paint); 

       break; 

     case MotionEvent.ACTION_UP: 
       if(((event.getX()>pointListDrawView.get(i+1).x-radius) && (event.getX()<pointListDrawView.get(i+1).x+radius) && (event.getY()>pointListDrawView.get(i+1).y-radius) && (event.getY()<pointListDrawView.get(i+1).y+radius))) 
       { 
        finalX=pointListDrawView.get(i+1).x; 
        finalY=pointListDrawView.get(i+1).y; 
        universalCanvas.drawLine(initialX,initialY, finalX,finalY, paint); 
        Log.d("touch", "line drawn"); 
        return true; 
       } 
       else 
       { 
        Log.d("touch", "correct point touched and discarded"); 
        return false; 
       } 


     default: 
      break; 

     } 
     invalidate(); 
     return true; 

    } 

} 
+1

在更新新的點之後,只需調用'invalidate()'。如果你調用'invalidate()',那麼'onDraw()'會再次調用。 – Shaiful

+0

請chk源代碼 –

+0

發表我的回答。檢查是否有幫助。 – Shaiful

回答

7

我只是爲你寫這段代碼。檢查是否有幫助。

import android.content.Context; 
import android.graphics.Canvas; 
import android.graphics.Color; 
import android.graphics.Paint; 
import android.graphics.Paint.Style; 
import android.graphics.PointF; 
import android.view.MotionEvent; 
import android.view.View; 

public class TestView extends View 
{ 

    private Paint paint; 
    private PointF startPoint, endPoint; 
    private boolean isDrawing; 

    public TestView(Context context) 
    { 
     super(context); 
     init(); 
    } 

    private void init() 
    { 
     paint = new Paint(); 
     paint.setColor(Color.RED); 
     paint.setStyle(Style.STROKE); 
     paint.setStrokeWidth(2); 
     paint.setAntiAlias(true); 
    } 

    @Override 
    protected void onDraw(Canvas canvas) 
    { 
     if(isDrawing) 
     { 
      canvas.drawLine(startPoint.x, startPoint.y, endPoint.x, endPoint.y, paint); 
     } 
    } 


    @Override 
    public boolean onTouchEvent(MotionEvent event) 
    { 
     switch (event.getAction()) 
     { 
      case MotionEvent.ACTION_DOWN: 
       startPoint = new PointF(event.getX(), event.getY()); 
       endPoint = new PointF(); 
       isDrawing = true; 
       break; 
      case MotionEvent.ACTION_MOVE: 
       if(isDrawing) 
       { 
        endPoint.x = event.getX(); 
        endPoint.y = event.getY(); 
        invalidate(); 
       } 
       break; 
      case MotionEvent.ACTION_UP: 
       if(isDrawing) 
       { 
        endPoint.x = event.getX(); 
        endPoint.y = event.getY(); 
        isDrawing = false; 
        invalidate(); 
       } 
       break; 
      default: 
       break; 
     } 
     return true; 
    } 
} 
+0

謝謝,非常感謝:) –

+0

非常輝煌的答案兄弟:) –

0

有兩種解決方案:

  1. 差,容易(這是回答你的問題:「如何在運行時繪製一條線,而不使用onDraw()?」) - 子類ImageView並在位圖上繪圖,然後更新ImageView
  2. 不錯,並有更多的工作 - 在onTouchEvent觸摸存儲歷史不繪製那裏,我的意思是存儲每個ACTION_DOWN ACTION_MOVE(記住關於多點觸控,因此存儲觸摸的ID在ACTION_DOWN並驗證它在ACTION_MOVE/ACTION_UP)!僅向下向上和移動呼叫無效。在onDraw方法中繪製這個歷史。在編輯中,你已經邁出了一大步,但你確實在那裏畫畫。