![](/img/trans.png)
[英]Using MountSpec component with “wrap_content” View - How to implement onMeasure()
[英]onMeasure(): wrap_content, how do I know the size to wrap?
我已经使用onDraw()
覆盖了自定义视图,在画布上绘制了一个位图。 当我在布局文件中指定我想要它wrap_content时,它仍然会填满整个屏幕。 onMeasure()
说:
measure的基类实现默认为背景大小,除非
MeasureSpec
允许更大的大小。 子类应覆盖onMeasure(int,int)以提供更好的内容测量。
好的,所以我知道我需要覆盖onMeasure()
并使用MeasureSpec
。 根据这个答案
unex表示layout_width或layout_height值设置为wrap_content。 你可以任意大小。
现在我遇到了我的问题,我如何在onMeasure()
测量我尚未创建的位图并测量/包装它? 我知道其他Android视图必须做一些事情,因为如果设置为wrap_content,它们不会阻挡整个屏幕。 提前致谢!
1. Constructor // choose your desired size
2. onMeasure // parent will determine if your desired size is acceptable
3. onSizeChanged
4. onLayout
5. onDraw // draw your view content at the size specified by the parent
如果你的视图可以是它想要的任何尺寸,它会选择多大的尺寸? 这将是您的wrap_content
大小,将取决于您的自定义视图的内容。 例子:
dp
到px
大小 。) 如果您想要的大小使用繁重的计算,那么在构造函数中执行此操作。 否则,你可以在onMeasure
分配它。 ( onMeasure
, onLayout
和onDraw
可能会被多次调用,这就是为什么在这里做繁重工作不好的原因。)
onMeasure
是孩子告诉父母有多大的地方,父母决定这是否可以接受。 这种方法经常被调用几次,每次都传递不同的大小要求,看看是否可以达到一些妥协。 但最后,孩子需要尊重父母的身材要求。
当我需要复习如何设置我的onMeasure
时,我总是回到这个答案 :
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int desiredWidth = 100;
int desiredHeight = 100;
int widthMode = MeasureSpec.getMode(widthMeasureSpec);
int widthSize = MeasureSpec.getSize(widthMeasureSpec);
int heightMode = MeasureSpec.getMode(heightMeasureSpec);
int heightSize = MeasureSpec.getSize(heightMeasureSpec);
int width;
int height;
//Measure Width
if (widthMode == MeasureSpec.EXACTLY) {
//Must be this size
width = widthSize;
} else if (widthMode == MeasureSpec.AT_MOST) {
//Can't be bigger than...
width = Math.min(desiredWidth, widthSize);
} else {
//Be whatever you want
width = desiredWidth;
}
//Measure Height
if (heightMode == MeasureSpec.EXACTLY) {
//Must be this size
height = heightSize;
} else if (heightMode == MeasureSpec.AT_MOST) {
//Can't be bigger than...
height = Math.min(desiredHeight, heightSize);
} else {
//Be whatever you want
height = desiredHeight;
}
//MUST CALL THIS
setMeasuredDimension(width, height);
}
在上面的示例中,所需的宽度和高度仅设置为某些默认值。 您可以事先计算它们并使用类成员变量在此处设置它们。
在onMeasure
之后,您的视图大小已知。 这个大小可能是您要求的,也可能不是您所要求的,但这是您现在必须使用的。 使用该大小在onDraw
上绘制视图上的内容。
invalidate()
。 这将导致再次调用onDraw
(但不是所有其他先前的方法)。 requestLayout()
。 这将从onMeasure
开始重新测量和绘制的过程。 它通常与对invalidate()
的调用相结合 。 invalidate()
)。 这看起来有点浪费,因为您要求整个视图层次结构连续布局两次。 如果在onMeasure调用之前无法测量位图,则可以返回大小为零,直到加载位图。 加载后,使父ViewGroup无效以强制执行另一个度量(不记得View本身上的invalidate()是否会强制onMeasure)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.