Tips for creating a view on Android and creating a view on android
[OnMeasure]
The custom control that directly inherits the view or ViewGroup must override the onMeasure method and set its own size when wrap_content is used. Otherwise, using wrap_content in the layout is equivalent to match_parent.
@ Override protected void onMeasure (int widthMeasureSpec, int heightMeasureSpec) {int widthMode = MeasureSpec. getMode (widthMeasureSpec); int heightMode = MeasureSpec. getMode (heightMeasureSpec); int widthSize = MeasureSpec. getSize (widthMeasureSpec); int heightSize = MeasureSpec. getSize (heightMeasureSpec); int width = 100; // adjust the default value according to your needs. int height = 100; // adjust the default value based on your needs. if (widthMode = MeasureSpec. AT_MOST & heightMode = MeasureSpec. AT_MOST) {setMeasuredDimension (width, height);} else if (widthMode = MeasureSpec. AT_MOST) {setMeasuredDimension (width, heightSize);} else if (heightMode = MeasureSpec. AT_MOST ){
SetMeasuredDimension (widthSize, height );
}
}
// LinearLayout calls onMeasure through measure
ViewGroup is an abstract class with an abstract method onLayout; The onMeasure method is not rewritten, but a measureChildren method is provided to measure each child element.
The onMeasure measurement process of ViewGroup is generally rewritten in its subclass. For example, onMeasure in LinearLayout will first judge the linear direction, and then traverse the measurement (each sub-element is executed
MeasureChildBeforeLayout () method. This method calls the measure () method of the child element to measure its own size.) After the child element is measured, LinearLayout measures its own size.
SetMeasuredDimension (resolveSizeAndState (maxWidth, widthMeasureSpec, childState), heightSizeAndState );
View is not an abstract class
In each life cycle of an Activity, onCreat and onResume may not be able to obtain the precise width and height of the View, because the measurement process of the View and the life cycle of the Activity are not synchronized.
Solution: 1. Execute View. getMeasuredWidth () in onWindowFocusChanged of view ()
[OnLayout] // LinearLayout calls onLayout through layout
The layout method determines the position of the View, while the onLayout method calls the layout method of the child element to determine the position of the child element through setChildFrame.
[OnDraw]
Call the following four methods using the draw method:
1. draw the background. draw (canvas ).
2. Draw your own onDraw (canvas ).
3. Draw children (dispatchDraw (canvas )).
4. onDrawScrollBars (canvas )).
View rendering is implemented through dispatchDraw. (In ViewGroup) dispatchDraw traverses the draw method of all child elements, so that the draw event can be passed through layers.
ViewRoot corresponds to the ViewRootImpl class, which is the link connecting WindowManager and Deco View (FrameLayout.
Notice on creating a custom View:
1. Enable View to support wrap_content;
2. If necessary, make your View support padding: this is because the View control is inherited directly. If you do not process paddong in the draw method, the padding attribute will not work. In addition, controls inherited from ViewGroup must consider the impact of padding and sub-element margin on onMeasure and onLayout. Otherwise, the margin of padding and sub-elements will become invalid.
3. Do not use handler in the View as much as possible. It is unnecessary because the View itself has the post series method, which can replace handler.
4. If a thread or animation exists in the View, stop it in time. For details, see View # onDetachedFromWindow.