import java.util.ArrayList; import com.example.exmcustom.R; import android.annotation.SuppressLint; import android.content.Context; import android.content.res.TypedArray; import android.graphics.Bitmap; import android.graphics.Bitmap.Config; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Path; import android.util.AttributeSet; import android.util.Log; import android.view.MotionEvent; import android.view.View; public class SignatureView extends View { private static final String TAG = "SignatureView"; private Paint paint; private Canvas cacheCanvas; private Bitmap cachebBitmap; private Path path; private int paint_color = Color.BLACK; private int stroke_width = 3; private PathPosition pos = new PathPosition(); private ArrayList<PathPosition> pathArray = new ArrayList<PathPosition>(); private int mWidth=0, mHeight=0; public SignatureView(Context context,AttributeSet attrs) { super(context, attrs); if (attrs != null) { TypedArray attrArray=getContext().obtainStyledAttributes( attrs, R.styleable.SignatureView); paint_color = attrArray.getColor(R.styleable.SignatureView_paint_color, Color.BLACK); stroke_width = attrArray.getInt(R.styleable.SignatureView_stroke_width, 3); attrArray.recycle(); } } public SignatureView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); if (attrs != null) { TypedArray attrArray=getContext().obtainStyledAttributes( attrs, R.styleable.SignatureView); paint_color = attrArray.getColor(R.styleable.SignatureView_paint_color, Color.BLACK); stroke_width = attrArray.getColor(R.styleable.SignatureView_stroke_width, 3); attrArray.recycle(); } } public SignatureView(Context context) { super(context); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); mWidth = this.getMeasuredWidth(); mHeight = this.getMeasuredHeight(); Log.d(TAG, "onMeasure width="+mWidth+",height="+mHeight); init(mWidth, mHeight); } public SignatureView(Context context, int width, int height) { super(context); init(width, height); } public int getPaintColor() { return paint_color; } public void setPaintColor(int paint_color) { this.paint_color = paint_color; } public int getStrokeWidth() { return stroke_width; } public void setStrokeWidth(int stroke_width) { this.stroke_width = stroke_width; } public Bitmap getCachebBitmap() { return getDrawingCache(); } private void init(int width, int height) { paint = new Paint(); paint.setAntiAlias(true); paint.setStrokeWidth(stroke_width); paint.setStyle(Paint.Style.STROKE); paint.setColor(paint_color); path = new Path(); setDrawingCacheEnabled(true); cachebBitmap = Bitmap.createBitmap(width, height, Config.ARGB_8888); cacheCanvas = new Canvas(cachebBitmap); cacheCanvas.drawColor(Color.WHITE); } public void clear() { if (cacheCanvas != null) { pathArray.clear(); cacheCanvas.drawRGB(255, 255, 255); invalidate(); } } public void revoke() { if (pathArray.size() > 0) { pathArray.remove(pathArray.size()-1); cacheCanvas.drawRGB(255, 255, 255); for (int i=0; i<pathArray.size(); i++) { Path posPath = new Path(); posPath.moveTo(pathArray.get(i).firstX, pathArray.get(i).firstY); posPath.quadTo(pathArray.get(i).firstX, pathArray.get(i).firstY, pathArray.get(i).nextX, pathArray.get(i).nextY); cacheCanvas.drawPath(posPath, paint); } invalidate(); } } @SuppressLint("DrawAllocation") @Override protected void onDraw(Canvas canvas) { canvas.drawBitmap(cachebBitmap, 0, 0, null); canvas.drawPath(path, paint); //这个是需要的,最近一次的路径保存在这里 } private float cur_x, cur_y; @SuppressLint("ClickableViewAccessibility") @Override public boolean onTouchEvent(MotionEvent event) { float x = event.getX(); float y = event.getY(); switch (event.getAction()) { case MotionEvent.ACTION_DOWN: cur_x = x; cur_y = y; path.moveTo(cur_x, cur_y); pos.firstX = cur_x; pos.firstY = cur_y; break; case MotionEvent.ACTION_MOVE: path.quadTo(cur_x, cur_y, x, y); cur_x = x; cur_y = y; pos.nextX = cur_x; pos.nextY = cur_y; pathArray.add(pos); pos = new PathPosition(); pos.firstX = cur_x; pos.firstY = cur_y; break; case MotionEvent.ACTION_UP: cacheCanvas.drawPath(path, paint); path.reset(); break; } invalidate(); return true; } }