在Android中,有时我们需要测量控件的宽度和高度进行一些运算,特别是在自适应屏幕的时候,这些计算就变得特别必要,但是,如果我们直接在onCreate,或者onStart、onResume(第一次执行时)方法,去获取控件的宽度和高度时,得出的结果会是0。</span>
原因是,在执行这几个方法时,窗口Window对象并没有创建完成,而只是做了一些初始化的操作,想要获取控件的宽度和高度就要等到onDraw方法执行完成之后。那么我们怎么知道,控件什么时候绘制完成,并切去获取控件的宽度和高度呢。
方式一、Android为我们提供了这样的机制,利用View类中getViewTreeObserver()方法,为控件添加一个观察者,在控件绘制前进行回调,这样我么就可以获取控件绘制完成之后的宽度以及高度:
tv.getViewTreeObserver().addOnPreDrawListener(new OnPreDrawListener() {
@Override
public boolean onPreDraw() {
if (!hasDraw) {
Log.e(TAG,
tv.getMeasuredWidth() + "=="
+ tv.getMeasuredWidth());
hasDraw = true;
}
return true;
}
});
方式二:监听View的可视状态的变化,View进行绘制之后,可视状态会改变,这时候我们就可以使用View类中的getViewTreeObserver().addOnGlobalLayoutListener,来给控件添加一个观察者:
tv.getViewTreeObserver().addOnGlobalLayoutListener(new OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
Log.e(TAG,
tv.getMeasuredWidth() + "=="
+ tv.getMeasuredWidth());
}
});
方式三、
int w = View.MeasureSpec.makeMeasureSpec(0,
View.MeasureSpec.UNSPECIFIED);
int h = View.MeasureSpec.makeMeasureSpec(0,
View.MeasureSpec.UNSPECIFIED);
tv.measure(w, h);
int height = tv.getMeasuredHeight();
int width = tv.getMeasuredWidth();
Log.e(TAG, width + "==" + height);
该方法有肯出现空指针异常,原因未知,不过在给控件设置LayoutParams之后,异常消失。
方式四、
在Activity的onWindowFocusChaged()方法中去获取控件的宽度和高度