invalidate与requestLayout的区别
invalidate()与requestLayout()是view中的方法
代码添加一个自定义view,view显示在屏幕上的工作流程:
new CustomView->ViewGroup.addView(CustomView)->measure->onMeasure->layout->onLayout->draw->onDraw(绘制自己)->dispatchDraw(绘制子视图)
invalidate()
/**
* Invalidate the whole view. If the view is visible,
* {@link #onDraw(android.graphics.Canvas)} will be called at some point in
* the future.
* <p>
* This must be called from a UI thread. To call from a non-UI thread, call
* {@link #postInvalidate()}.
*/
public void invalidate() {
invalidate(true);
}
这个方法是用来刷新整个视图的,当视图的内容,可见性发生变化,onDraw(Canvas canvas)方法会被调用。
注意:
1.调用invalidate()方法不会导致measure和layout方法被调用,具体原因可看源码。
2.如果视图是viewGroup,其子view的内容或者位置变化,调用invalidate()方法,因为对viewGroup而言,其大小和位置并没有发生变化。
3.invalidate()方法必须在UI线程中调用,如果想在非UI线程中调用,则使用postInvalidate()
requestLayout()
/**
* Call this when something has changed which has invalidated the
* layout of this view. This will schedule a layout pass of the view
* tree. This should not be called while the view hierarchy is currently in a layout
* pass ({@link #isInLayout()}. If layout is happening, the request may be honored at the
* end of the current layout pass (and then layout will run again) or after the current
* frame is drawn and the next layout occurs.
*
* <p>Subclasses which override this method should call the superclass method to
* handle possible request-during-layout errors correctly.</p>
*/
@CallSuper
public void requestLayout() {
...
}
requestLayout()是在view的布局发生变化时调用,布局的变化包含位置,大小。
注意:
1.这个方法不能在正在布局的时候调用
2.调用这个方法,会导致布局重绘,调用measure,layout,draw的过程。