For reprinting, please indicate the source: http://blog.csdn .NET/lmj623565791/article/details/24500107
A friend has such a need today (the following picture), I think that custom View is still very suitable to do, so do the following, by the way, and share with you, for custom View more practice is not bad. If you read the first two articles, then this one must be so easy.
The effect is like this. After analysis, there are probably these attributes, two colors, one speed, and the width of a circle.
Or the steps we took to customize the View:
1. Properties of custom View
2. Obtain our custom attributes in View's construction method
[3. Rewrite onMesure]
4. Rewrite onDraw
--------------------
1. Custom Properties:
- <?xml version="1.0" encoding="utf-8"?>
- <resources>
- <attr name="firstColor" format="color" />
- <attr name="secondColor" format="color" />
- <attr name="circleWidth" format="dimension" />
- <attr name="speed" format="integer" />
- <declare-styleable name="CustomProgressBar">
- <attr name="firstColor" />
- <attr name="secondColor" />
- <attr name="circleWidth" />
- <attr name="speed" />
- </declare-styleable>
- </resources>
<?xml version="1.0" encoding="utf-8"?> <resources> <attr name="firstColor" format="color" /> <attr name="secondColor" format="color" /> <attr name="circleWidth" format="dimension" /> <attr name="speed" format="integer" /> <declare-styleable name="CustomProgressBar"> <attr name="firstColor" /> <attr name="secondColor" /> <attr name="circleWidth" /> <attr name="speed" /> </declare-styleable> </resources>
2. Obtain our custom attributes in View's construction method
- /**
- * The color of the first circle
- */
- private int mFirstColor;
- /**
- * The color of the second circle
- */
- private int mSecondColor;
- /**
- * Width of circle
- */
- private int mCircleWidth;
- /**
- * Paint brush
- */
- private Paint mPaint;
- /**
- * Current progress
- */
- private int mProgress;
- /**
- * speed
- */
- private int mSpeed;
- /**
- * Should we start the next one?
- */
- private boolean isNext = false;
- public CustomProgressBar(Context context, AttributeSet attrs)
- {
- this(context, attrs, 0);
- }
- public CustomProgressBar(Context context)
- {
- this(context, null);
- }
- /**
- * Necessary initialization to get some custom values
- *
- * @param context
- * @param attrs
- * @param defStyle
- */
- public CustomProgressBar(Context context, AttributeSet attrs, int defStyle)
- {
- super(context, attrs, defStyle);
- TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.CustomProgressBar, defStyle, 0);
- int n = a.getIndexCount();
- for (int i = 0; i < n; i++)
- {
- int attr = a.getIndex(i);
- switch (attr)
- {
- case R.styleable.CustomProgressBar_firstColor:
- mFirstColor = a.getColor(attr, Color.GREEN);
- break;
- case R.styleable.CustomProgressBar_secondColor:
- mSecondColor = a.getColor(attr, Color.RED);
- break;
- case R.styleable.CustomProgressBar_circleWidth:
- mCircleWidth = a.getDimensionPixelSize(attr, (int) TypedValue.applyDimension(
- TypedValue.COMPLEX_UNIT_PX, 20, getResources().getDisplayMetrics()));
- break;
- case R.styleable.CustomProgressBar_speed:
- mSpeed = a.getInt(attr, 20);//Default 20
- break;
- }
- }
- a.recycle();
- mPaint = new Paint();
- //Drawing thread
- new Thread()
- {
- public void run()
- {
- while (true)
- {
- mProgress++;
- if (mProgress == 360)
- {
- mProgress = 0;
- if (!isNext)
- isNext = true;
- else
- isNext = false;
- }
- postInvalidate();
- try
- {
- Thread.sleep(mSpeed);
- } catch (InterruptedException e)
- {
- e.printStackTrace();
- }
- }
- };
- }.start();
- }
/** * The color of the first circle */ private int mFirstColor; /** * The color of the second circle */ private int mSecondColor; /** * Width of circle */ private int mCircleWidth; /** * Brush */ private Paint mPaint; /** * Current progress */ private int mProgress; /** * Speed */ private int mSpeed; /** * Should we start the next one? */ private boolean isNext = false; public CustomProgressBar(Context context, AttributeSet attrs) { this(context, attrs, 0); } public CustomProgressBar(Context context) { this(context, null); } /** * Necessary initialization to get some custom values * * @param context * @param attrs * @param defStyle */ public CustomProgressBar(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.CustomProgressBar, defStyle, 0); int n = a.getIndexCount(); for (int i = 0; i < n; i++) { int attr = a.getIndex(i); switch (attr) { case R.styleable.CustomProgressBar_firstColor: mFirstColor = a.getColor(attr, Color.GREEN); break; case R.styleable.CustomProgressBar_secondColor: mSecondColor = a.getColor(attr, Color.RED); break; case R.styleable.CustomProgressBar_circleWidth: mCircleWidth = a.getDimensionPixelSize(attr, (int) TypedValue.applyDimension( TypedValue.COMPLEX_UNIT_PX, 20, getResources().getDisplayMetrics())); break; case R.styleable.CustomProgressBar_speed: mSpeed = a.getInt(attr, 20); //Default 20 break; } } a.recycle(); mPaint = new Paint(); // Drawing thread new Thread() { public void run() { while (true) { mProgress++; if (mProgress == 360) { mProgress = 0; if (!isNext) isNext = true; else isNext = false; } postInvalidate(); try { Thread.sleep(mSpeed); } catch (InterruptedException e) { e.printStackTrace(); } } }; }.start(); }
3. Rewrite onDraw directly without rewriting onMeasure
- @Override
- protected void onDraw(Canvas canvas)
- {
- int centre = getWidth() / 2; //Obtaining the x-coordinates of the center of a circle
- int radius = centre - mCircleWidth / 2;//Radius
- mPaint.setStrokeWidth(mCircleWidth); //Set the width of the ring
- mPaint.setAntiAlias(true); //Elimination of serrations
- mPaint.setStyle(Paint.Style.STROKE); //Hollow
- RectF oval = new RectF(centre - radius, centre - radius, centre + radius, centre + radius); //The boundaries of the shape and size of the defined arc
- if (!isNext)
- {//The circle of the first color is complete, and the second color runs.
- mPaint.setColor(mFirstColor); //Set the color of the ring
- canvas.drawCircle(centre, centre, radius, mPaint); //Draw a circle
- mPaint.setColor(mSecondColor); //Set the color of the ring
- canvas.drawArc(oval, -90, mProgress, false, mPaint); //Draw an arc according to schedule
- } else
- {
- mPaint.setColor(mSecondColor); //Set the color of the ring
- canvas.drawCircle(centre, centre, radius, mPaint); //Draw a circle
- mPaint.setColor(mFirstColor); //Set the color of the ring
- canvas.drawArc(oval, -90, mProgress, false, mPaint); //Draw an arc according to schedule
- }
- }
@Override protected void onDraw(Canvas canvas) { Int center = getWidth ()/ 2; // Get the x coordinates of the center of the circle int radius = centre - mCircleWidth / 2; // radius mPaint.setStrokeWidth(mCircleWidth); // Set the width of the ring mPaint.setAntiAlias(true); //Eliminate serrated teeth mPaint.setStyle(Paint.Style.STROKE);//Set hollow RectF oval = new RectF(centre - radius, centre - radius, centre + radius, centre + radius); // The boundaries of shape and size used to define arcs if (!isNext) {// The circle of the first color is complete, and the second color runs. mPaint.setColor(mFirstColor); // Set the color of the ring canvas.drawCircle(centre, centre, radius, mPaint); // Draw a circle mPaint.setColor(mSecondColor); // Set the color of the ring canvas.drawArc(oval, -90, mProgress, false, mPaint); // Draw an arc according to progress } else { mPaint.setColor(mSecondColor); // Set the color of the ring canvas.drawCircle(centre, centre, radius, mPaint); // Draw a circle mPaint.setColor(mFirstColor); // Set the color of the ring canvas.drawArc(oval, -90, mProgress, false, mPaint); // Draw an arc according to progress } }
Great success has been achieved, of course, the only thing that is more tangled is when the two colors switch, how to switch, I use the above method, you can also think about how to achieve.
Okay, you guys, leave a message, top one.~