Android custom control series 2: Custom switch button (1), android Control
This time, we will implement a complete and pure custom control, instead of using the system control like the previous Composite Control. The plan is divided into three parts:Basic Part of the custom control,Processing of touch events of Custom ControlsAndCustom properties of a custom control;
Next we will start writing the first part. This time we will take a defined switch button as an example. Here we will start:
First, let's take a look at the effect. Click the switch button to switch the switch status:
In order to be clear, let's give some basic introductions.
The first thing to clarify is whether the custom control inherits the View class. Google provides a lot of methods in the View class for us to use, using these methods, we can implement a lot of effects and functions. here we need to use several main methods;
Steps and main methods used for custom controls:
1. First, define a class that inherits the View. For classes that inherit the View, at least one constructor is required. In fact, there are three constructor methods:
Public View (Context context)It is called when the java code creates a view (using the new method). If the view is filled in xml, this
Public View (Context context, AttributeSet attrs)This is called when xml is created but no style is specified.
Public View (Context context, AttributeSet attrs, int defStyle)This is called when adding a style on the second basis.
Therefore, if style is not used, we should focus on the second constructor.
2. For any control that needs to be displayed on our interface, you must define its size. Here Google provides a method:Protected void onMeasure (int widthMeasureSpec, int heightMeasureSpec );Let's look at the interior of this method. Actually, it is called.Protected final void setMeasuredDimension (int measuredWidth, int measuredHeight );In this method, the first parameter is the view width, and the second parameter is the view height. In this way, we can set the view width and height,However, you must note that the units set in this way are pixels.
3. For a control to be displayed, we often need to determine its position: This requires rewriting.OnLayoutMethod, but in fact this method is not used much in custom view, because for the location, the control has only the suggestion right and has no decision, and the decision is generally in the parent control.
4. For a control, we need to display it. Of course we need to draw it out. Here we need to override the onDraw method to draw this control.
5. When the control status changes, we may need to refresh the display status of the view. At this time, we need to call the invalidate () method. This method will actually re-call the onDraw method to repaint the control.
6. You can directly useSetOnClickListenerYou do not need to write view. setOnClickListener;
7. Define the custom control in the layout file. Note that the full class name should be used for the name. In addition, because the custom control inherits from the view control, therefore, you can directly use the view attributes in an xml file, for example:Android: layout_widthAnd so on.
ComparisonKey PointsThis is whereOnDrawMethod. Let's take a look:
/*** Method of drawing the view. Draw the content of the current view */@ Overrideprotected void onDraw (Canvas canvas) {// super. onDraw (canvas); Paint paint = new Paint (); // open the anti-sawtooth paint. setAntiAlias (true); // draws the canvas background. drawBitmap (backgroundBitmap, 0, 0, paint); // draw the slider canvas. drawBitmap (slideButton, slideBtn_left, 0, paint );}
OnDrawThe input parameter isCanvasCanvas object, which is actually not much different from Java. We need a paint brush to draw on the canvas. We will initialize it here.Paint paint = new Paint ()And set an anti-sawtooth effect.Paint. setAntiAlias (true)And then callDrawBitmapThe background of the switch and the slider of the switch are drawn:
Note that,DrawBitmap (Bitmap bitmap, float left, float top, painting)The two float parameters in the middle of the method represent the coordinates of x and y in the upper left corner of the drawing (the origin is set in the upper left corner), so if we input 0, 0, the switch will be in the off State. Here, we use a variable for the slider.SlideBtn_leftTo set its location,For the off status, the value of slideBtn_left should be 0. For the on status, the value of slideBtn_left should be the width of the backgroundBitmap (background) minus the width of the slideButton (slider ).;
In this way, the mechanism is clear. We only need to set a click event on the control, and set a boolean variable to indicate the status of the switch. When you click, change the value of this boolean type to true or false.SlideButtonIs0OrBackgroundBitmap. getWidth ()-slideButton. getWidth ()And then callInvalidate ()Method to refresh the control to implement the basic switch function.
The specific code is shown below, and the annotations are more detailed:
The custom control class MyToggleButton. java inherits from View:
Package com. example. togglebutton. ui; import com. example. togglebutton. r; import android. content. context; import android. graphics. bitmap; import android. graphics. bitmapFactory; import android. graphics. canvas; import android. graphics. paint; import android. util. attributeSet; import android. view. view;/** steps for customizing a view: * 1. First, you must write a class to inherit the View. * 2. To obtain the view object, you must override the constructor, the construction method of one of the parameters is used for new, and the construction method of the two parameters is used for the xml layout file. The construction method of the three parameters can be passed in A style * 3. To set the view size, you must override the onMeasure Method * 4. To set the view location, you must override the onLayout method, however, this method is not used much in custom views because the position of the view is mainly determined by the parent control * 5. You need to draw the view to be displayed, you need to override the onDraw Method * 6. When the control status changes, you need to re-paint the view, then call invalidate (); method, this method actually calls the onDraw method again * 7. If you need to set a click event for the view, you can directly call the setOnClickListener Method */public class MyToggleButton extends View {/*** background of the switch button */private Bitmap backgroundBitmap; /*** slide part of the switch button */private Bitmap slide Button;/*** left border of the sliding Button */private float slideBtn_left;/*** current switch status */private boolean currentState = false; /*** when creating an object in the code, use this constructor ** @ param context */public MyToggleButton (Context context) {super (context );} /*** the view declared in the layout file, which is automatically called by the system during creation ** @ param context * @ param attrs */public MyToggleButton (Context context, AttributeSet attrs) {super (context, attrs); initView () ;}/ *** callback Method for dimension measurement */@ Overridepr Otected void onMeasure (int widthMeasureSpec, int heightMeasureSpec) {// super. onMeasure (widthMeasureSpec, heightMeasureSpec); // set the size of the current view. width: view width. Unit: pixel value. heigth: view height. Unit: setMeasuredDimension (backgroundBitmap. getWidth (), backgroundBitmap. getHeight ();} // This method is not helpful for custom views, because the position of the view is generally determined by the parent component @ Overrideprotected void onLayout (boolean changed, int left, int top, int right, int bottom) {sup Er. onLayout (changed, left, top, right, bottom);}/*** Method for drawing the current view content */@ Overrideprotected void onDraw (Canvas canvas) {// super. onDraw (canvas); Paint paint = new Paint (); // open the anti-sawtooth paint. setAntiAlias (true); // draws the canvas background. drawBitmap (backgroundBitmap, 0, 0, paint); // draw the slider canvas. drawBitmap (slideButton, slideBtn_left, 0, paint);}/*** initialize view */private void initView () {backgroundBitmap = BitmapFactory. d EcodeResource (getResources (), R. drawable. switch_background); slideButton = BitmapFactory. decodeResource (getResources (), R. drawable. slide_button);/** Click Event */setOnClickListener (new OnClickListener () {@ Overridepublic void onClick (View v) {currentState =! CurrentState; flushState (); flushView () ;}});}/*** refresh view */protected void flushView () {// refresh the current view will cause the ondraw method to execute invalidate ();}/*** refresh the current status */protected void flushState () {if (currentState) {slideBtn_left = backgroundBitmap. getWidth ()-slideButton. getWidth () ;}else {slideBtn_left = 0 ;}}}
Define it in the layout file:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context="${relativePackage}.${activityClass}" > <com.example.togglebutton.ui.MyToggleButton android:id="@+id/my_toggle_btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" /></RelativeLayout>
As there is no logic to trigger the business by clicking any button here, it is just a simple control, so no code is added to MainActivity:
package com.example.togglebutton;import android.app.Activity;import android.os.Bundle;public class MainActivity extends Activity {@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);}}
Now a custom switch button is complete. The next two articles will introduce how to implementClick to drag the switchAnd how to implement Custom Attributes. Thank you for your support!
Android Custom Controls
Controls all belong to the View class
Visibility attributes: VISIBLE, INVISIBLE, and GONE
You can call the setVisibility method, for example
TextView txt;
Txt. setVisibility (View. GONE); // The control disappears!
Txt. setVisibility (View. VISIBLE); // The control appears again!
Alternatively, you can use a ViewStub control to dynamically load layout files.
It may not be suitable for your problem. How can I search it by myself?
Hope to help you
How can I determine whether to rewrite the android custom control?
Rewrite the two constructor methods.