Reprint please indicate source: http://blog.csdn.net/lmj623565791/article/details/24252901
A lot of Android starter Programs ape for Android Custom view, may be more scary, but this is the only way to master advanced, all ready to spend some time on the custom view, write more articles. First summarize the steps for customizing the view:
1. Custom View Properties
2. Get our custom properties in the View construction method
[3, rewrite onmesure]
4. Rewrite OnDraw
I marked 3 with [], so say 3 is not necessarily necessary, of course, most of the cases still need to rewrite.
1, custom View properties, first create a attrs.xml under Res/values/, define our properties and declare our entire style.
<?XML version= "1.0" encoding= "Utf-8"?> <Resources> <attrname= "TitleText"format= "string" /> <attrname= "Titletextcolor"format= "Color" /> <attrname= "Titletextsize"format= "Dimension" /> <declare-styleablename= "Customtitleview"> <attrname= "TitleText" /> <attrname= "Titletextcolor" /> <attrname= "Titletextsize" /> </declare-styleable> </Resources>
We define the font, font color, font size 3 properties, format is the value type of the property:
Altogether there are: string,color,demension,integer,enum,reference,float,boolean,fraction,flag; it's not clear that Google can do it.
Then declare our custom view in the layout
<Relativelayoutxmlns:android= "Http://schemas.android.com/apk/res/android"Xmlns:tools= "Http://schemas.android.com/tools"Xmlns:custom= "Http://schemas.android.com/apk/res/com.example.customview01"Android:layout_width= "Match_parent"Android:layout_height= "Match_parent" > <com. Example.customview01.view.CustomTitleView android:layout_width= "200DP"Android:layout_height= "100DP"Custom:titletext= "3712"Custom:titletextcolor= "#ff0000"custom:titletextsize= "40SP" /> </Relativelayout>
Be sure to introduce xmlns:custom= "http://schemas.android.com/apk/res/com.example.customview01" to our namespace, followed by a package path that refers to the project's
2, in the construction method of view, get our custom style
/*** Text*/ PrivateString Mtitletext; /*** Color of text*/ Private intMtitletextcolor; /*** Size of text*/ Private intmtitletextsize; /*** Control the range of text drawing when drawing*/ PrivateRect Mbound; PrivatePaint Mpaint; PublicCustomtitleview (Context context, AttributeSet attrs) { This(context, Attrs, 0); } PublicCustomtitleview (Context context) { This(Context,NULL); } /*** get my own custom style attributes * *@paramContext *@paramAttrs *@paramDefstyle*/ PublicCustomtitleview (context context, AttributeSet attrs,intDefstyle) { Super(context, attrs, Defstyle); /*** Get the custom style attributes we've defined*/TypedArray a= Context.gettheme (). Obtainstyledattributes (Attrs, R.styleable.customtitleview, Defstyle, 0); intn =A.getindexcount (); for(inti = 0; I < n; i++) { intattr =A.getindex (i); Switch(attr) { CaseR.styleable.customtitleview_titletext:mtitletext=a.getstring (attr); Break; CaseR.styleable.customtitleview_titletextcolor://The default color is set to blackMtitletextcolor =A.getcolor (attr, Color.Black); Break; Caser.styleable.customtitleview_titletextsize://The default setting is 16sp,typevalue can also convert SP to PXMtitletextsize = A.getdimensionpixelsize (attr, (int) Typedvalue.applydimension (TYPEDVALUE.COMPLEX_UNIT_SP, 16, Getresources (). Getdisplaymetrics ()); Break; }} a.recycle (); /*** Get the width and height of the drawn text*/Mpaint=NewPaint (); Mpaint.settextsize (mtitletextsize); //Mpaint.setcolor (mtitletextcolor);Mbound =NewRect (); Mpaint.gettextbounds (Mtitletext,0, Mtitletext.length (), mbound); }
We have rewritten 3 constructor methods, the default layout file is called the construction method of two parameters, so remember to let all constructs call our three parameters of the construction, we in three parameters of the construction of the custom properties.
3, we rewrite the ondraw,onmesure call system to provide the
@Override protected void onmeasure ( Heightmeasurespec) { super Span style= "color: #000000;" >.onmeasure (Widthmeasurespec, Heightmeasurespec); } @Override protected void OnDraw (Canvas canvas) {mpaint.setcolor (color.yellow); Canvas.drawrect ( 0, 0/2-mbound.width ()/2, GetHeight ()/2 + mbound.height ()/2, Mpaint); }
The effect at this point is:
Whether it feels good, basically has implemented a custom view. But at this point if we write the width and height of the layout file as Wrap_content, we will find that the effect is not our expectation:
The system helps us measure the height and width are match_parnet, when we set the clear width and height, the system helps us measure the result is we set the result, when we set to Wrap_content, or Match_ The result that the parent system helps us measure is the length of the match_parent.
So, when Wrap_content is set, we need to do our own measurements, that is, rewrite the Onmesure method ":
Before rewriting, understand Measurespec's specmode, altogether three kinds:
Exactly: The general setting of a definite value or a match_parent
At_most: Indicates that the child layout is limited to a maximum value, typically warp_content
UNSPECIFIED: Indicates how large a sub-layout is to be, rarely used
Here is our rewrite Onmeasure code:
@Overrideprotected voidOnmeasure (intWidthmeasurespec,intHeightmeasurespec) { intWidthmode =Measurespec.getmode (WIDTHMEASURESPEC); intWidthsize =measurespec.getsize (WIDTHMEASURESPEC); intHeightmode =Measurespec.getmode (HEIGHTMEASURESPEC); intHeightsize =measurespec.getsize (HEIGHTMEASURESPEC); intwidth; intheight; if(Widthmode = =measurespec.exactly) {width=widthsize; } Else{mpaint.settextsize (mtitletextsize); Mpaint.gettextbounds (Mtitle,0, Mtitle.length (), mbounds); floatTextWidth =mbounds.width (); intdesired = (int) (Getpaddingleft () + TextWidth +getpaddingright ()); Width=desired; } if(Heightmode = =measurespec.exactly) {height=heightsize; } Else{mpaint.settextsize (mtitletextsize); Mpaint.gettextbounds (Mtitle,0, Mtitle.length (), mbounds); floatTextHeight =mbounds.height (); intdesired = (int) (Getpaddingtop () + TextHeight +Getpaddingbottom ()); Height=desired; } setmeasureddimension (width, height); }
Now let's modify the layout file:
<Relativelayoutxmlns:android= "Http://schemas.android.com/apk/res/android"Xmlns:tools= "Http://schemas.android.com/tools"Xmlns:custom= "Http://schemas.android.com/apk/res/com.example.customview01"Android:layout_width= "Match_parent"Android:layout_height= "Match_parent" > <com. Example.customview01.view.CustomTitleView android:layout_width= "Wrap_content"Android:layout_height= "Wrap_content"Custom:titletext= "3712"android:padding= "10DP"Custom:titletextcolor= "#ff0000"android:layout_centerinparent= "true"custom:titletextsize= "40SP" /> </Relativelayout>
Now the effect is:
Completely compound our expectations, now we can be the height, width of the casual set, the basic can meet our needs.
Of course, this way down our custom view is not much of an advantage compared to TextView, all we feel for adding an event to a custom view:
In the construct, add:
this. Setonclicklistener (new Onclicklistener () { @Override public void OnClick (View v) { = randomtext (); Postinvalidate (); } });
PrivateString Randomtext () {random random=NewRandom (); Set<Integer> set =NewHashset<integer>(); while(Set.size () < 4) { intRandomint = Random.nextint (10); Set.add (Randomint); } stringbuffer SB=NewStringBuffer (); for(Integer i:set) {sb.append ("" +i); } returnsb.tostring (); }
Run it again below:
*android Custom View