Android 获取 View 宽高
01.获取View宽高的方式
1.1 onWindowFocusChanged
如下所示
1
2
3
4
5
6
7
8@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
if (hasFocus) {
int width = view.getMeasuredWidth();
int height = view.getMeasuredHeight();
}
}
1.2 view.post(runnable)
如下所示
1
2
3
4
5
6
7view.post(new Runnable() {
@Override
public void run() {
int width = view.getMeasuredWidth();
int height = view.getMeasuredHeight();
}
});
1.3 ViewTreeObserver
如下所示
1
2
3
4
5
6
7
8
9ViewTreeObserver observer = view.getViewTreeObserver();
observer.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
int width = view.getMeasuredWidth();
int height = view.getMeasuredHeight();
}
});
1.4 手动测量控件宽高
如下所示
1
2
3
4
5int w = View.MeasureSpec.makeMeasureSpec(0,View.MeasureSpec.UNSPECIFIED);
int h = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
imageView.measure(w, h);
int height = imageView.getMeasuredHeight();
int width = imageView.getMeasuredWidth();
02.onWindowFocusChanged
- 该方法的含义是:View已经初始化完毕了,宽/高已经准备好了,所以此时去获取宽/高是没有问题的。
- 注意:onWindowFocusChanged会被调用多次,当activity的窗口得到焦点和失去焦点时均会被调用一次
- 具体来说,当activity继续执行(onResume)和暂停执行(onPause)时,onWindowFocusChanged均会被调用。
03.view.post(runnable)
- 通过post可以将一个runnable投递到消息队列的尾部,然后等待Looper调用此runnable时,View也已经初始化好了。
04.ViewTreeObserver
- 使用ViewTreeObserver的众多回调也可以完成这个功能,比如使用OnGlobalLayoutListener这个接口。当View树的状态发生改变或者View树内部的View的可见性发生改变时,onGlobalLayout方法将被调用。
- 注意:伴随着View树的状态改变等,onGlobalLayout会被调用多次。因此需要在适当时机将监听回调移除。
05.手动测量控件宽高
- 比其他的方法多调用了一次onMeasure()方法,该方法虽然看上去简单,但是如果要目标控件计算耗时比较大的话(如listView等),不建议使用
- 如果是简单的button,textView等控件,用该方法也可以