我想让用户在View中绘制一些东西。但是我遇到一行问题,因为我的覆盖ACTION_UP
事件的onTouch
永远不会被调用。我尝试使用switch case语句和if else。我听说ACTION_DOWN
必须返回true才能调用ACTION_UP
。但这对我没有用。
以下是相关代码:
public class Drawing extends View {
//drawing path
private Path drawPath;
//drawing and canvas paint
private Paint drawPaint, canvasPaint;
//initial color
private int paintColor = 0xFF660000;
//canvas
private Canvas drawCanvas;
//canvas bitmap
private Bitmap canvasBitmap;
private Context contextDrawing;
public Drawing(Context context, View zeichnungsview/*, AttributeSet attrs*/){
super(context/*, attrs*/);
contextDrawing = context;
//View drawingView = (View) findViewById(R.id.zeichnenView);
LayoutInflater inflater = LayoutInflater.from(contextDrawing);
//View.inflate(contextDrawing, R.layout.openproject, null);
//Log.d("drawingView", "drawingView " + inflater + "|" + drawingView);
zeichnungsview.setOnTouchListener(drawingOnTouchListener);
setupDrawing();
}
//setup drawing
private void setupDrawing(){
//prepare for drawing and setup paint stroke properties
drawPath = new Path();
drawPaint = new Paint();
drawPaint.setColor(Color.BLACK);
drawPaint.setAntiAlias(true);
drawPaint.setStrokeWidth(20);
drawPaint.setStyle(Paint.Style.STROKE);
drawPaint.setStrokeJoin(Paint.Join.ROUND);
drawPaint.setStrokeCap(Paint.Cap.ROUND);
canvasPaint = new Paint(Paint.DITHER_FLAG);
//LayoutInflater inflater = (LayoutInflater) contextDrawing.getSystemService( Context.LAYOUT_INFLATER_SERVICE );
//View drawingView = (View) inflater.inflate(R.layout.openproject, null);
//View drawingView = (View) findViewById(R.id.zeichnenView);
//drawingView.setOnTouchListener(drawingOnTouchListener);
}
final OnTouchListener drawingOnTouchListener = new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
float touchX = event.getX();
float touchY = event.getY();
int action = event.getAction();
int code = action & MotionEvent.ACTION_MASK;
Log.d("touchX", "touchX " + touchX + "|" + event.getAction());
//respond to down, move and up events
if(code == MotionEvent.ACTION_DOWN){
Log.d("ACTION_DOWN", "ACTION_DOWN");
drawPath.moveTo(touchX, touchY);
}
if (code == MotionEvent.ACTION_UP) {
drawPath.lineTo(touchX, touchY);
drawCanvas.drawPath(drawPath, drawPaint);
drawPath.reset();
}
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.d("ACTION_DOWN", "ACTION_DOWN");
drawPath.moveTo(touchX, touchY);
return true;
case MotionEvent.ACTION_MOVE:
Log.d("ACTION_MOVE", "ACTION_MOVE");
drawPath.lineTo(touchX, touchY);
return true;
case MotionEvent.ACTION_UP:
Log.d("ACTION_UP", "ACTION_UP");
drawPath.lineTo(touchX, touchY);
drawCanvas.drawPath(drawPath, drawPaint);
drawPath.reset();
break;
default:
return false;
}
//redraw
invalidate();
return true;
}
};
//size assigned to view
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
canvasBitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
drawCanvas = new Canvas(canvasBitmap);
}
//draw the view - will be called after touch event
@Override
protected void onDraw(Canvas canvas) {
canvas.drawBitmap(canvasBitmap, 0, 0, canvasPaint);
canvas.drawPath(drawPath, drawPaint);
}
//register user touches as drawing action
@Override
public boolean onTouchEvent(MotionEvent event) {
float touchX = event.getX();
float touchY = event.getY();
Log.d("touchX", "touchX " + touchX);
//respond to down, move and up events
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
drawPath.moveTo(touchX, touchY);
drawPath.lineTo(touchX, touchY);
drawCanvas.drawPath(drawPath, drawPaint);
drawPath.reset();
break;
case MotionEvent.ACTION_MOVE:
drawPath.lineTo(touchX, touchY);
break;
case MotionEvent.ACTION_UP:
drawPath.lineTo(touchX, touchY);
drawCanvas.drawPath(drawPath, drawPaint);
drawPath.reset();
break;
default:
return false;
}
//redraw
invalidate();
return true;
}
//update color
public void setColor(String newColor){
invalidate();
paintColor = Color.parseColor(newColor);
drawPaint.setColor(paintColor);
}
}
我仍然遇到无效的问题。所以我尝试了一个简单的例子。在这里,当我点击视图时,只绘制一个矩形。没有Action_Up,但我遇到了问题,onDraw( )
方法永远不会被调用。除此之外,我不知道如何从另一个完全打电话给班级。
所以这是我的主要活动(在这种情况下我用new Drawing(context)
尝试过):
final OnClickListener zeichnenViewClickListener = new OnClickListener(){
@Override
public void onClick(View v) {
Log.d("zeichnenViewClickListener", "zeichnenViewClickListener ");
final Drawing view = new Drawing(context);
view.postInvalidate();
}
};
这会调用Drawing构造函数而不是onDraw( )
方法:
public class Drawing extends View {
public Drawing(Context context) {
super(context);
Log.d("Drawing", "Drawing");
invalidate();
}
@Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
Log.d("Drawing0", "Drawing0");
super.onDraw(canvas);
Log.d("Drawing1", "Drawing1");
Rect rect = new Rect();
rect.set(0, 0, canvas.getWidth(), canvas.getHeight() / 2);
Paint blue = new Paint();
blue.setColor(Color.BLUE);
blue.setStyle(Paint.Style.FILL);
Log.d("Drawing2", "Drawing2");
canvas.drawRect(rect, blue);
Log.d("Drawing3", "Drawing3");
}
}
我想在此视图中绘制线条(现在仅用于测试目的,只需点击一个矩形):
查看
android:id="@+id/zeichnenView"
android:layout_width="400dp"
android:layout_height="400dp"
class="com.unitnode.Drawing"
android:background="#FFFFFF" />
那么Drawing.class类必须如何从main Activity调用,为什么onDraw( )
永远不会被调用?