Android Canvas Draw by finger

后端 未结 2 1382
無奈伤痛
無奈伤痛 2020-12-29 16:20

On a project I’m working on at my current job, I’ve come across some really pernicious problems where there is either

no good information available or
the go         


        
相关标签:
2条回答
  • 2020-12-29 16:53
    1. Create a class that extends View and paste below code.

    public class CustomClass extends View {
    
      private Paint paint = new Paint();
      private Path path = new Path();
    
      public CustomClass(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
        paint.setAntiAlias(true);
        paint.setStrokeWidth(5 f);
        paint.setColor(Color.BLACK);
        paint.setStyle(Paint.Style.STROKE);
        paint.setStrokeJoin(Paint.Join.ROUND);
      }
    
      @Override protected void onDraw(Canvas canvas) {
        canvas.drawPath(path, paint);
      }
    
      @Override public boolean onTouchEvent(MotionEvent event) {
        // Get the coordinates of the touch event.
        float eventX = event.getX();
        float eventY = event.getY();
    
        switch (event.getAction()) {
          case MotionEvent.ACTION_DOWN:
            // Set a new starting point
            path.moveTo(eventX, eventY);
            return true;
          case MotionEvent.ACTION_MOVE:
            // Connect the points
            path.lineTo(eventX, eventY);
            break;
          default:
            return false;
        }
    
        // Makes our view repaint and call onDraw
        invalidate();
        return true;
      }
    
    }

    2 In XML, paste below code

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="#ffffff">
    
        <!-- This is the view on which we will draw. -->
        <view
            android:layout_width="match_parent"
            android:layout_height="200sp"
            class="com.example.gopal.drawing.MainDrawingView"
            android:id="@+id/custom_view"
            android:layout_gravity="left|top"
            android:background="#ffffff" />
    
        <View
            android:id="@+id/boundary"
            android:layout_width="match_parent"
            android:layout_height="2sp"
            android:background="@color/colorAccent"
            android:layout_below="@id/custom_view"/>
    
        <ImageView
            android:id="@+id/image"
            android:layout_width="300sp"
            android:layout_height="300sp"
            android:src="@drawable/ic_launcher_background"
            android:layout_below="@id/boundary"
            android:layout_marginTop="6sp"
            android:layout_centerHorizontal="true"/>
    
        <Button
            android:id="@+id/button"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="save"
            android:layout_alignParentBottom="true"
            android:layout_centerHorizontal="true"
            android:onClick="saveImage"/>
    
    </RelativeLayout>

    3 Your MainActivity

    public class MainActivity extends AppCompatActivity {
    
      ImageView imageView;
      @Override
      protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        imageView = findViewById(R.id.image);
      }
    
      public void saveImage(View view) {
        View v = findViewById(R.id.custom_view);
        int canvasWidth = v.getWidth();
        int canvasHeight = v.getHeight();
        Bitmap bitmap = Bitmap.createBitmap(canvasWidth, canvasHeight, Bitmap.Config.ARGB_8888);
        Canvas canvas = new Canvas(bitmap);
        v.draw(canvas);
        imageView.setImageBitmap(bitmap);
    
      }
    
    }

    That's it.

    0 讨论(0)
  • 2020-12-29 17:04

    Follow these steps:

    1) Create a view class then extends View, Also create constructor

    override the onDraw(). You add the path of where finger touches and moves. You override the onTouch() of this purpose. In your onDraw() you draw the paths using the paint of your choice. You should call invalidate() to refresh the view.

    //drawing path
        static Path drawPath;
        //drawing and canvas paint
        private Paint drawPaint, canvasPaint;
        //initial color
        static int paintColor = 0xFFFF0000; 
        //stroke width
        private  float STROKE_WIDTH = 5f;
        //canvas
        private Canvas drawCanvas;
        //canvas bitmap
        private Bitmap canvasBitmap;
        //eraser mode
        private boolean erase=false;
    
        //constructor
        public DrawingView(Context context, AttributeSet attrs){
            super(context, attrs);
            setupDrawing();
            setErase(erase);
        }
    
    
            private void setupDrawing(){
                drawPath = new Path();
                drawPaint = new Paint();
                drawPaint.setColor(paintColor);
                drawPaint.setAntiAlias(true);
                drawPaint.setStrokeWidth(STROKE_WIDTH);
                drawPaint.setStyle(Paint.Style.STROKE);
                drawPaint.setStrokeJoin(Paint.Join.ROUND);
                drawPaint.setStrokeCap(Paint.Cap.ROUND);
                canvasPaint = new Paint(Paint.DITHER_FLAG);
            }
    
            //*************************************** View assigned size  ****************************************************
    
            @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);
            }
    
            public void setErase(boolean isErase){
                erase=isErase;
            drawPaint = new Paint();
            if(erase) { 
                setupDrawing();
                int srcColor= 0x00000000;
    
                PorterDuff.Mode mode = PorterDuff.Mode.CLEAR;
                PorterDuffColorFilter porterDuffColorFilter = new PorterDuffColorFilter(srcColor, mode);
    
                drawPaint.setColorFilter(porterDuffColorFilter);
    
                drawPaint.setColor(srcColor);
                drawPaint.setXfermode(new PorterDuffXfermode(mode));
    
            }
            else {
    
                setupDrawing();
    
            }
            }
    
            //************************************   draw view  *************************************************************
    
            @Override
            protected void onDraw(Canvas canvas) {
                canvas.drawBitmap(canvasBitmap, 0, 0, canvasPaint);
                canvas.drawPath(drawPath, drawPaint);
            }
    
            //***************************   respond to touch interaction   **************************************************
    
            @Override
            public boolean onTouchEvent(MotionEvent event) {
    
                canvasPaint.setColor(paintColor);
                float touchX = event.getX();
                float touchY = event.getY();
                //respond to down, move and up events
    
                switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    drawPath.moveTo(touchX, touchY);
                    break;
                case MotionEvent.ACTION_MOVE:
                    drawCanvas.drawPath(drawPath, drawPaint);
                    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;
            }
    
            //***********************************   return current alpha   ***********************************************
            public int getPaintAlpha(){
                return Math.round((float)STROKE_WIDTH/255*100);
            }
    
            //**************************************  set alpha   ******************************************************
            public void setPaintAlpha(int newAlpha){
                STROKE_WIDTH=Math.round((float)newAlpha/100*255);
                drawPaint.setStrokeWidth(newAlpha);
        }
            }
    

    2) Your Activity:-

    SeekBar mThickness;
    private DrawingView mDrawLayout;
    Button erase, draw;
    private Paint drawPaint = new Paint();
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        mThickness = (SeekBar) findViewById(R.id.thickness);
        mDrawLayout = (DrawingView) findViewById(R.id.viewDraw);
        erase = (Button) findViewById(R.id.erase);
        draw= (Button) findViewById(R.id.draw);
    
        mDrawLayout.setVisibility(View.VISIBLE);
        mDrawLayout.setDrawingCacheEnabled(true);
        mDrawLayout.setEnabled(true);
        mThickness.setMax(50);
        mThickness.setProgress(10);
        mDrawLayout.setPaintAlpha(mThickness.getProgress());
        int currLevel = mDrawLayout.getPaintAlpha();
        mThickness.setProgress(currLevel);
        mDrawLayout.invalidate();
    
        erase.setOnClickListener(new OnClickListener() {
    
            @Override
            public void onClick(View v) {
                drawPaint.setColor(Color.TRANSPARENT);
                mDrawLayout.setErase(true);
    
            }
        });
    
        draw.setOnClickListener(new OnClickListener() {
    
            @Override
            public void onClick(View v) {
                mDrawLayout.setErase(false);
    
            }
        });
    
        mThickness.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
    
            @Override
            public void onStopTrackingTouch(SeekBar seekBar) {
            }
    
            @Override
            public void onStartTrackingTouch(SeekBar seekBar) {
            }
    
            @Override
            public void onProgressChanged(SeekBar seekBar, int progress,
                    boolean fromUser) {
                mDrawLayout.setPaintAlpha(mThickness.getProgress());
            }
        });
    }
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        // Inflate the menu; this adds items to the action bar if it is present.
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }
    

    3) xml:-

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        tools:context=".MainActivity" >
    
        <com.example.drawdemo.DrawingView
            android:id="@+id/viewDraw"
            android:layout_width="wrap_content"
            android:layout_height="200dp"
            android:layout_marginTop="20dp"
            android:scaleType="fitXY" />
    
        <SeekBar
            android:id="@+id/thickness"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_below="@+id/viewDraw"
            android:layout_marginTop="25dp" />
    
        <Button
            android:id="@+id/erase"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_below="@+id/thickness"
            android:text="erase" />
    
        <Button
            android:id="@+id/draw"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_below="@+id/erase"
            android:text="draw" />
    
    </RelativeLayout>
    
    0 讨论(0)
提交回复
热议问题