Reputation: 93
How could I fill the green portion between two arcs shown below using the paint and canvas methods?
Here is how I draw the two arcs, I also could figure out how to connect them with lines but I don't know how I can fill the inner area.
// set to stroke black
paint.setColor(Color.BLACK);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeWidth((float) STROKE_WIDTH);
// outside arc
RectF arc_oval_outside = new RectF((float) (getX()), (float) (getY()),
(float) (getX() + getWidth()), (float) (getY() + getHeight()));
canvas.drawArc(arc_oval_outside, (float) (0.0), (45.0) (ARC_SWEEP), false, paint);
// inside arc
RectF arc_oval_inside = new RectF((float) (getX() + ARC_WIDTH), (float) (getY() + ARC_WIDTH),
(float) (getX() + getWidth() - ARC_WIDTH), (float) (getY() + getHeight() - ARC_WIDTH));
canvas.drawArc(arc_oval_inside, (float) (0.0), (float) (ARC_SWEEP), false, paint);
Upvotes: 7
Views: 5793
Reputation: 3312
Just posting another option using drawArc only. Basically we first draw the outer filled arc and then we draw the smaller inner arc using PorterDuff.Mode.CLEAR to erase and achieve the asked above.
Bitmap b = Bitmap.createBitmap(1200, 1200, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(b);
int radius = 40;
float startAngle = 45f; // your start angle
float sweepAngle = 90f; // your sweep angle
Paint paint = new Paint();
paint.setAntiAlias(true);
paint.setColor(Color.rgb(37, 181, 215));
paint.setStyle(Paint.Style.FILL);
// draw outer arc
RectF oval = new RectF(0, 0, canvas.getWidth(), canvas.getHeight());
canvas.drawArc(oval, startAngle, sweepAngle, true, paint);
// draw inner arc
paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
oval = new RectF((canvas.getWidth() / 2) - radius, (canvas.getHeight() / 2) - radius, (canvas.getWidth() / 2) + radius, (canvas.getHeight() / 2) + radius);
canvas.drawArc(oval, startAngle, sweepAngle, true, paint);
ImageView.setImageBitmap(b);
Hope it helps someone.
Upvotes: 1
Reputation: 11137
Here is a simple way to draw filled arc with border:
Point center = new Point(canvas.getWidth()/2, canvas.getHeight()/2);
int inner_radius = 100;
int outer_radius = 150;
int arc_sweep = 90;
int arc_ofset = 30;
RectF outer_rect = new RectF(center.x-outer_radius, center.y-outer_radius, center.x+outer_radius, center.y+outer_radius);
RectF inner_rect = new RectF(center.x-inner_radius, center.y-inner_radius, center.x+inner_radius, center.y+inner_radius);
Path path = new Path();
path.arcTo(outer_rect, arc_ofset, arc_sweep);
path.arcTo(inner_rect, arc_ofset + arc_sweep, -arc_sweep);
path.close();
Paint fill = new Paint();
fill.setColor(Color.GREEN);
canvas.drawPath(path, fill);
Paint border = new Paint();
border.setStyle(Paint.Style.STROKE);
border.setStrokeWidth(2);
canvas.drawPath(path, border);
(The Path
and Paint
allocation is made to be clear not optimal)
Upvotes: 9
Reputation: 171
I Know it could be a little bit late but I came with this approach from a iOS project, first draw contour and then draw the filling arc
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
float width = (float)getWidth();
float height = (float)getHeight();
float radius;
//Get radius from the bigger size
if (width > height){
radius = height/2;
}else{
radius = width/2;
}
//Create Paint Object
Paint paint = new Paint();
paint.setColor(Color.RED);
paint.setFilterBitmap(true);
paint.setAntiAlias(true);
paint.setStrokeWidth(5);
paint.setStyle(Paint.Style.STROKE);
//Create Contour Object
Path path = new Path();
float center_x, center_y;
center_x = width/2;
center_y = height/2;
//Configure rect for the outer ring
final RectF oval = new RectF();
oval.set(center_x - radius + 5,
center_y - radius + 5,
center_x + radius - 5,
center_y + radius - 5);
//Add outer arc
path.addArc(oval, 0, 90);
//Configure rect for the inner ring
oval.set(center_x - radius + 30,
center_y - radius + 30,
center_x + radius - 30,
center_y + radius - 30);
//Add inner arc to the path but draw counterclockwise
path.arcTo(oval, -270, -90);
//close path
path.close();
//Create Paint Object
Paint fillPaint = new Paint();
fillPaint.setColor(Color.YELLOW);
fillPaint.setFilterBitmap(true);
fillPaint.setAntiAlias(true);
fillPaint.setStrokeWidth(21);
fillPaint.setStyle(Paint.Style.STROKE);
//Create Contour Object
Path fillPath = new Path();
//Configure rect for the fill ring
oval.set(center_x - radius + 17,
center_y - radius + 17,
center_x + radius - 17,
center_y + radius - 17);
//Add fill arc
fillPath.addArc(oval, 0, 90);
//draw fill path
canvas.drawPath(fillPath,fillPaint);
//draw outer path
canvas.drawPath(path, paint);
}
A helpfull link: http://www.programering.com/a/MDO1czNwATE.html where addarc maths are quite well explained
Upvotes: 1