Freehand Image Crop draw inside bitmap region

2019-03-15 22:44发布

问题:

Trying to achieve freehand cropping of an image, so I'm able to draw on the image. But it goes outside bitmap region. I just wanna restrict that user can only draw inside bitmap region, check below screen shot.

I am trying to implement functionality like Photoshop lasso tool.

Its drawing outside view region, which generates incorrect output.

Output

Code@

onDraw

public void onDraw(Canvas canvas) {

        final Rect rect = new Rect(0, 0, bitmap.getWidth(), bitmap.getHeight());
        canvas.drawBitmap(bitmap, rect, rect, null);
        // RectF r = new RectF();
        // Matrix matrix = new Matrix();
        // matrix.mapRect(r);
        // Log.i(TAG, "Rect " + r.left + " " + r.top + " " + r.right + " " +
        // r.bottom + " ");
        // canvas.clipRect(r.left, r.top, r.right, r.bottom);

        Path path = new Path();
        boolean first = true;

        for (int i = 0; i < points.size(); i += 2) {
            Point point = points.get(i);
            if (first) {
                first = false;
                path.moveTo(point.x, point.y);
            } else if (i < points.size() - 1) {
                Point next = points.get(i + 1);
                path.quadTo(point.x, point.y, next.x, next.y);
            } else {
                mlastpoint = points.get(i);
                path.lineTo(point.x, point.y);
            }
        }
        canvas.drawPath(path, paint);
    }

onCrop

Bitmap resultingImage = Bitmap.createBitmap(widthOfscreen,heightOfScreen, bitmap1.getConfig());

        Canvas canvas = new Canvas(resultingImage);

        Paint paint = new Paint();
        paint.setAntiAlias(true);
        Path path = new Path();
        for (int i = 0; i < SomeView.points.size(); i++) {
            path.lineTo(SomeView.points.get(i).x, SomeView.points.get(i).y);
        }
        // path.lineTo(150, 0);
        // path.lineTo(230, 120);
        // path.lineTo(70, 120);
        // path.lineTo(150, 0);

        canvas.drawPath(path, paint);
        if(crop){
            paint.setXfermode(new PorterDuffXfermode(Mode.SRC_IN));

        }else{
            paint.setXfermode(new PorterDuffXfermode(Mode.SRC_OUT));
        }

suggest me to achieve my goal.

回答1:

late answer but use full for other u can override onmeasure method and set your image bitmap width and height in that method and resize your canvas so now you can draw only in your canvas.so your image come center.it for drawpath only on your bitmap.

 @Override
public void onMeasure(int widthMeasureSpec, int heightMeasureSpec){
    super.onMeasure(widthMeasureSpec, heightMeasureSpec);

    height = bitmap.getHeight();
    width = bitmap.getWidth();

    setMeasuredDimension(width,height);
}

and then change in your oncrop method so you can slove it esaly.

Bitmap resultingImage = Bitmap.createBitmap(yourbitmap.getwidth(),yourbitmap.getheight(), yourbitmap.getConfig());


回答2:

There is one way to achieve your goal..

Follow below steps:

1) Make one image like as inside part of crop image should be transparent and outside part should be background of canvas check below Image.

2) Draw that image on top of your canvas.

3) Draw anything on your canvas and drawagain that image on top of the canvas.

Image:



回答3:

You can ignore all Touch Events that are outside your image view. Remember the last event location that is inside your image view and connect it with the next event location that is inside the view. This should work when both events are part of a single movement (without lifting your finger), but it might be more complicated when the drawing is done outside your view and then a new drawing starts inside. Try to cover this case too.