无标题文章

package com.example.arcapplication;

import android.content.Context;

import android.graphics.Bitmap;

import android.graphics.BitmapFactory;

import android.graphics.Canvas;

import android.graphics.Color;

import android.graphics.Matrix;

import android.graphics.Paint;

import android.graphics.Path;

import android.graphics.PathMeasure;

import android.graphics.Point;

import android.graphics.PointF;

import android.graphics.Rect;

import android.graphics.RectF;

import android.text.TextPaint;

import android.util.AttributeSet;

import android.util.Log;

import android.view.View;

import androidx.annotation.Nullable;

public class ArcView extends View {

    private Paint mPaint;

    private TextPaint mTextPaint;

    private Bitmap mBitmap;

    private Path mPath;

    private PathMeasure mPathMeasure;

    private float mLength;

    private float[] pos;

    private float[] tan;

    public ArcView(Context context) {

        this(context, null);

    }

    public ArcView(Context context, @Nullable AttributeSet attrs) {

        this(context, attrs, 0);

    }

    public ArcView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {

        super(context, attrs, defStyleAttr);

        mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);

        mPaint.setStrokeCap(Paint.Cap.ROUND);

        mPaint.setStyle(Paint.Style.STROKE);

        mPaint.setStrokeWidth(12);

        mTextPaint = new TextPaint(Paint.ANTI_ALIAS_FLAG);

        mTextPaint.setStrokeCap(Paint.Cap.ROUND);

        mTextPaint.setStyle(Paint.Style.STROKE);

        mTextPaint.setTextSize(26);

        mTextPaint.setColor(Color.BLACK);

        mBitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.ic_battery2);

        mRect = new RectF();

        mRect.set((float) (getWidth() / 2f - mRadius), (float) (getHeight() / 2f - mRadius),

                (float) (getWidth() / 2f + mRadius), (float) (getHeight() / 2f + mRadius));

        mOuterRect = new RectF();

        mOuterRect.set((float) (getWidth() / 2f - mOuterRadius), (float) (getHeight() / 2f - mOuterRadius),

                (float) (getWidth() / 2f + mOuterRadius), (float) (getHeight() / 2f + mOuterRadius));

        float top = mTextPaint.getFontMetrics().top;

        float bottom = mTextPaint.getFontMetrics().bottom;

        float offsetV = ((itemWidth) / 2) - bottom;

        mOuterIconRect = new RectF();

        mOuterIconRect.set(mOuterRect.left - offsetV ,mOuterRect.top - offsetV ,

                mOuterRect.right + offsetV  ,mOuterRect.bottom  + offsetV);

        baseLine =

                (mTextPaint.getFontMetrics().descent

                        - mTextPaint.getFontMetrics().ascent) / 2 - mTextPaint.getFontMetrics().descent;

        mPath = new Path();

        mPathMeasure = new PathMeasure();

    }

    float baseLine;

    @Override

    protected void onDraw(Canvas canvas) {

        super.onDraw(canvas);

        canvas.translate(getWidth() / 2f, getHeight() / 2f);

        mPaint.setColor(Color.BLUE);

        canvas.drawArc(mRect, 0, 360, false, mPaint);

        mPaint.setColor(Color.RED);

        canvas.drawArc(mOuterRect, 0, 360, false, mPaint);

        drawUp(canvas, 180 + 90 - 56);

        drawUp(canvas, 180 + 90 - 24);

        drawUp(canvas, 180 + 90 + 6);

        drawDown(canvas, 180 - 90 + 56);

        drawDown(canvas, 180 - 90 + 24);

        drawDown(canvas, 180 - 90 - 6);

    }

    private void drawUp(Canvas canvas, int degrees){

        mPath.reset();

        mPath.addArc(mOuterIconRect, 0, 360);

        mPathMeasure.setPath(mPath, false);

        mLength = mPathMeasure.getLength();

        pos = new float[2];

        tan = new float[2];

        canvas.save();

        mPathMeasure.getPosTan(mLength * (degrees / 360f), pos, tan);

        canvas.rotate(degrees, pos[0], pos[1]);mPaint.setColor(Color.RED);

        RectF rectF = new RectF(pos[0] - itemWidth/2, pos[1] - itemWidth/2,

                pos[0] + itemWidth/2, pos[1] + itemWidth/2);

        canvas.drawRect(rectF, mPaint);

        canvas.restore();

        // 角度弧度互换

        // Math.toDegrees(angrad);            //角度转换成弧度,返回:angrad * 180d / PI

        // Math.toRadians(angdeg);            //弧度转换成角度,返回:angdeg / 180d * PI

        mPath.reset();

        mPath.addArc(mOuterRect.left, mOuterRect.top,mOuterRect.right, mOuterRect.bottom,

                degrees, 18);

        canvas.drawTextOnPath("100%", mPath, 15,0f, mTextPaint);

        PointF point = drawArcIcon(250, degrees);

        mPaint.setColor(Color.RED);

        canvas.drawPoint(point.x, point.y, mPaint);

    }

    private void drawDown(Canvas canvas, int degrees){

        mPath.reset();

        mPath.addArc(mOuterIconRect, 0, 360);

        mPathMeasure.setPath(mPath, false);

        mLength = mPathMeasure.getLength();

        pos = new float[2];

        tan = new float[2];

        canvas.save();

        mPathMeasure.getPosTan(mLength * (degrees / 360f), pos, tan);

        canvas.rotate(degrees, pos[0], pos[1]);mPaint.setColor(Color.RED);

        RectF rectF = new RectF(pos[0] - itemWidth/2, pos[1] - itemWidth/2,

                pos[0] + itemWidth/2, pos[1] + itemWidth/2);

        canvas.drawRect(rectF, mPaint);

        canvas.restore();

        // 角度弧度互换

        // Math.toDegrees(angrad);            //角度转换成弧度,返回:angrad * 180d / PI

        // Math.toRadians(angdeg);            //弧度转换成角度,返回:angdeg / 180d * PI

        mPath.reset();

        mPath.addArc(mOuterRect.left, mOuterRect.top,mOuterRect.right, mOuterRect.bottom,

                degrees, -18);

        canvas.drawTextOnPath("100%", mPath, 15, Math.abs(mTextPaint.getFontMetrics().top)-baseLine, mTextPaint);

        PointF point = drawArcIcon(250, degrees);

        mPaint.setColor(Color.RED);

        canvas.drawPoint(point.x, point.y, mPaint);

    }

    private final RectF mRect;

    private final RectF mOuterRect;

    private final RectF mOuterIconRect;

    private float mRadius = 216;

    private float mOuterRadius = 250;

    private float itemWidth = 30;

    private PointF drawArcIcon(float radius, float startAngle) {

        // 计算,中心点到menu item中心的距离

        float x = (float) (Math.cos(Math.toRadians(startAngle)) * radius);

        float y = (float) (Math.sin(Math.toRadians(startAngle)) * radius);

        Log.d("wyj", "x : " + x + ", y : " + y);

        return new PointF(x, y);

    }

}

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容