1. This article will introduce you to the custom progress bar writing, relatively simple, but there are some points of knowledge to be noted:
Invalidate () method
The application of RECTF method
The application of Onmeasure method
2. Principle
Draw a 3-story rounded rectangle with black at the bottom, a gray in the second, and a progress bar at the top level, as shown in the following example:
3. Effect drawing
There are many other ways to implement a fillet progress bar, such as filling a fillet picture in a progress control, and stretching the image to achieve the desired effect, although it sounds simple enough to be a bit cumbersome to achieve.
4. Explanation method
(1) Invalidate () method
Invalidate () is used to refresh view, and must work in the UI thread. For example, when you modify the display of a view, call invalidate () to see the redrawn interface. The call to Invalidate () POPs the old view from the main UI thread queue. This method is commonly used in custom controls.
(2) Application of RECTF method
RECTF is a way to paint a rectangle.
RECTF (Left,top,right,bottom), the meaning of four parameters is the distance between the parent control and the left upper right margin of the rectangle, as shown in the following illustration:
The Drawroundrect method is used to draw rounded rectangles, and its arguments are as follows:
Parameter description
RECT:RECTF object.
The radius of the fillet in the rx:x direction.
The radius of the fillet in the ry:y direction.
Paint: The brush that is used when drawing.
(3) Onmeasure method
Specifies the size of the custom control on the screen, the two parameters of the Onmeasure method are the size passed in by the previous control, and the values are mixed with the pattern and size, requiring Measurespec.getmode (WIDTHMEASURESPEC) to get the pattern. Measurespec.getsize (Widthmeasurespec) Gets the size.
Several models of Onmeasure were exactly,at_most,unspecified.
[1] measurespec.exactly
Measurespec.exactly is the exact size when we specify the control's Layout_width or Layout_height as a specific value, such as andorid:layout_width= "50dip", or Fill_ Parent is, the size of the control has been determined by the case, are the exact size.
[2] Measurespec.at_most
Measurespec.at_most is the largest size, and when the control's layout_width or layout_height is specified as wrap_content, the size of the control typically changes with the control's subspace or content. The size of the control can be as long as it does not exceed the maximum size allowed by the parent control. Therefore, the mode at this point is at_most,size gives the maximum size allowed by the parent control.
[3] Measurespec.unspecified
Measurespec.unspecified is not a specified size, this situation is not much, generally is the parent control is adapterview, through the measure method of the mode passed in.
5.activity_main.xml file:
<linearlayout xmlns:android= "http://schemas.android.com/apk/res/android"
xmlns:tools= "http:// Schemas.android.com/tools "
android:id=" @+id/container "
android:layout_width=" Match_parent "
Android : layout_height= "match_parent"
tools:context= "com.example.progresstest.MainActivity"
tools:ignore= " Mergerootframe ">
<com.example.progresstest.progressviewtest
android:id=" @+id/progressbar "
Android:layout_width= "Wrap_content"
android:layout_height= "wrap_content"/>
</LinearLayout>
6.progressviewtest.java file
Package com.example.progresstest;
Import Android.content.Context;
Import Android.graphics.Canvas;
Import Android.graphics.Color;
Import Android.graphics.Paint;
Import Android.graphics.RectF;
Import Android.util.AttributeSet;
Import Android.view.View; public class Progressviewtest extends View {/** progress bar maximum/private float Maxcount;/** progress bar Current Value * * Private float Currentcount;
* * * Brush/private Paint mpaint;
private int mwidth,mheight; Public Progressviewtest (context, AttributeSet attrs, int defstyle) {Super (context, attrs, defstyle);//TODO Auto -generated constructor stub} public progressviewtest (context, AttributeSet attrs) {Super (context, attrs);//TOD O auto-generated Constructor stub} public progressviewtest [context] {super (context);//TODO auto-generated cons
Tructor stub}/*** * Set maximum progress value * @param maxcount/public void Setmaxcount (float maxcount) {this.maxcount = Maxcount;}
/** * Get maximum progress value/public double Getmaxcount () {return maxcount;}/*** * Set current progress value* @param currentcount */public void Setcurrentcount (float currentcount) {this.currentcount = currentcount > Maxcount ?
Maxcount:currentcount; /** * Invalidate () is used to refresh view, and must work in the UI thread. For example, when you modify the display of a view, * call Invalidate () to see the redrawn interface.
The call to Invalidate () POPs the old view from the main UI * thread queue.
* * Invalidate (); @Override protected void OnDraw (Canvas Canvas) {//TODO auto-generated Method Stub Super.ondraw (Canvas); mpaint = new P
Aint ();
Set Anti-aliasing effect Mpaint.setantialias (true);
Sets the brush color Mpaint.setcolor (color.black);
int round = MHEIGHT/2;
/** * RECTF: Draw the rectangle, four parameters are Left,top,right,bottom * Type is a single-precision floating-point number * * * RECTF RF = new RECTF (0, 0, mwidth, mheight);
/* Draw rounded Rectangle, background color is brush color/canvas.drawroundrect (RF, round, round, mpaint);
/* Set Progress internal is gray * * * Mpaint.setcolor (COLOR.RGB (211, 211, 211));
RECTF RECTBLACKBG = new RECTF (2, 2, mWidth-2, mHeight-2);
Canvas.drawroundrect (RECTBLACKBG, round, round, mpaint);
Set progress bar progress and color float section = Currentcount/maxcount; RECTF RECTPROGRESSBG = new RECTF (3, 3, (mWidth-3) *section, mHeight-3); if (section!=0.0f) {mpaint.setcolor (color.green);}
else{Mpaint.setcolor (color.transparent);} canvas.drawroundrect (RECTPROGRESSBG, round, round, mpaint); //dip * scale + 0.5f * (Dip >= 0? 1:-1) private int diptopx (int dip) {Float scale = GetContext (). Getresources (). GE
Tdisplaymetrics (). density; return (int) (DIP * scale + 0.5f * (Dip >= 0? 1:-1))/Plus 0.5 is for rounding}/** specifies the size of the custom control on the screen, and the two parameters of the Onmeasure method are passed in by the previous layer control * Size, and is the number of patterns and sizes mixed together, requires Measurespec.getmode (WIDTHMEASURESPEC) * Get mode, measurespec.getsize (WIDTHMEASURESPEC) to get the size * * * * * Override protected void onmeasure (int widthmeasurespec, int heightmeasurespec) {//TODO auto-generated method stub super.
Onmeasure (Widthmeasurespec, Heightmeasurespec);
int widthspecmode = Measurespec.getmode (Widthmeasurespec);
int heightspecmode = Measurespec.getmode (Heightmeasurespec);
int widthspecsize = measurespec.getsize (Widthmeasurespec);
int heightspecsize = measurespec.getsize (Heightmeasurespec); measurespec.exactly, exact size if (Widthspecmode == measurespec.exactly | | Widthspecmode = = measurespec.at_most) {mwidth = Widthspecsize;} else {mwidth = 0;}//measurespec.at_most, maximum size, as long as the parent control is not exceeded Maximum allowable size, measurespec.unspecified unspecified size if (Heightspecmode = = Measurespec.at_most | | heightspecmode = = measurespec.unspecified) {mheight = Diptopx ();} else {mheight = heightspecsize;}//Set the actual size of the control setmeasureddimension (mWi
DTH, mheight); }
}
Mainactivity.java File
Package com.example.progresstest;
Import android.support.v7.app.ActionBarActivity;
Import Android.os.Bundle;
Import Android.os.Handler;
Import Android.os.Message; public class Mainactivity extends Actionbaractivity {private progressviewtest progress; @Override protected void onCreate (Bundle savedinstancestate) {super.oncreate (savedinstancestate); Setcontentview (r.layout.activity_main); progress = (progressviewtest)
Findviewbyid (R.id.progressbar);
Progress.setmaxcount (100); New Thread (New Runnable () {@Override public void run () {//TODO auto-generated a stub for (int i = 0; I <=progre Ss.getmaxcount (); i++) {msg = new message (); msg.arg1 = i; msg.what = 0x01; handler.sendmessage (msg); try {//Every 0.1 seconds Progress 1 THREAD.SL
EEP (100);
catch (Interruptedexception e) {//TODO auto-generated catch block E.printstacktrace ();}}
}). Start (); } Handler Handler = new Handler () {public void Handlemessage (msg) {if (msg.what==0x01) {Progress.setcurrentcount (M
SG.ARG1);
}
}; }; }
The above is a small set to introduce the Android custom progress bar of the fillet horizontal progress bar example detailed, I hope to help you, if you have any questions please give me a message, small series will promptly reply to everyone. Here also thank you very much for the cloud Habitat Community website support!