最近公司需要做一個扇形按鈕,沒有現成的控件,是以隻能自己去自定義。
大緻需求如下:
其一:分為四個子產品,可以點選任何子產品,然後進行不同業務操作
其二:點選時,文字随之變化
效果如下:

實作思路及其簡要代碼:
1,繪制背景 :
//定義畫筆
paint.setColor(circleColor);
paint.setStrokeWidth(circleWidth);
paint.setAntiAlias(true);
paint.setStyle(Paint.Style.STROKE);
float x = (getWidth() - getHeight() / 2) / 2;
float y = getHeight() / 4;
//繪制半圓
RectF oval = new RectF(x, y, getWidth() - x, getHeight() - y);
canvas.drawArc(oval, 90, -180, false, paint);
//繪制隔線
paint.setColor(backgroundColor);
paint.setStyle(Paint.Style.FILL);
paint.setStrokeWidth(5);//圓環隔線的寬度
canvas.drawLine(center, center, center, 0, paint);
canvas.drawLine(center, center, (float) (center + 0.5 * center * Math.sqrt(3)), center * 1 / 2, paint);
canvas.drawLine(center, center, (float) (center + 0.5 * center * Math.sqrt(3)), center * 3 / 2, paint);
canvas.drawLine(center, center, center, center * 2, paint);
//繪制文字
paint.setColor(Color.WHITE);
paint.setTextSize(banciTextSize);
canvas.drawText(“一班”, (float) (center + 0.25 * center), (float) 0.4 * center, paint);
canvas.drawText(“二班”, (float) (center + 0.6 * center), center, paint);
canvas.drawText(“三班”, (float) (center + 0.3 * center), (float) (center + 0.7 * center), paint);
2,定義點選事件,
this.setOnTouchListener(onTouchListener);
1)定義關于方向枚舉
public enum Dir {
FIRST, SECOND, THIRD, UNDEFINE, CENTER
}
2)檢測點選方向和範圍
private Dir checkDir(float x, float y) {
Dir dir = Dir.CENTER;
if (Math.pow(y - center, 2) + Math.pow(x - center, 2) < Math.pow(center / 2, 2)) {// 判斷在中心圓圈内
dir = Dir.CENTER;
} else if (Math.pow(y - center, 2) + Math.pow(x - center, 2) > Math.pow(center, 2)) {// 判斷在最大的圓弧外
dir = Dir.UNDEFINE;
} else if (y < x && y + x < 2 * center) {
dir = Dir.FIRST;
} else if (y < x && y + x > 2 * center) {
dir = Dir.SECOND;
} else if (y > x) {
dir = Dir.THIRD;
}
return dir;
}
3)繪制點選的扇形
private void drawOnclikColor(Canvas canvas, Dir dir) {
float x = (getWidth() - getHeight() / 2) / 2;
float y = getHeight() / 4;
paint.setColor(Color.BLACK);
paint.setTextSize(banciTextSize);
RectF oval = new RectF(x, y, getWidth() - x, getHeight() - y);
switch (dir) {
case FIRST:
canvas.drawText("一班", (float) (center + 0.25 * center), (float) 0.4 * center, paint);
if (onChooseListener != null) {
onChooseListener.setChooseFirst(1);
}
break;
case SECOND:
canvas.drawText("二班", (float) (center + 0.6 * center), center, paint);
if (onChooseListener != null) {
onChooseListener.setChooseFirst(2);
}
break;
case THIRD:
canvas.drawText("三班", (float) (center + 0.3 * center), (float) (center + 0.7 * center), paint);
if (onChooseListener != null) {
onChooseListener.setChooseFirst(3);
}
break;
case CENTER:
if (onChooseListener != null) {
onChooseListener.setChooseFirst(0);
}
break;
default:
break;
}
paint.setStyle(Paint.Style.FILL);
}
3,定義接口,供外部調用
public interface OnChooseListener {
void setChooseFirst(int type);
}
public void setOnChooseListener(OnChooseListener onChooseListener) {
this.onChooseListener = onChooseListener;
}