在一个ViewGroup中强制进行重新布局,包括其所有的孩子 [英] Force re-layout on a viewgroup including all its children
问题描述
我写了一个自定义布局(延伸的FrameLayout
),可以被放大。其所有的孩子也是这将真正从获得的比例因子的自定义视图自己通过getter方法父,并通过设置缩放尺寸像
I am writing up a custom layout (which extends FrameLayout
) that can be zoomed in. All its children are also custom views which would actually get the scale factor from their parent via a getter method and scale accordingly by setting the scaled dimensions like
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
float scaleFactor = ((CustomLayout) getParent()).getCurrentScale();
setMeasuredDimension((int) (getMeasuredWidth() * scaleFactor), (int) (getMeasuredHeight() * scaleFactor));
}
我使用的是 ScaleGestureDetector
来检测捏放大的姿态,改变布局的比例因子。然后,我通过调用 requestLayout
强迫自定义布局的布局。不幸的是这似乎并没有对其子女有任何影响。孩子们的 onMeasure
&安培; onLayout
即使父经过其措施和放大器永远不会调用;布局周期。但是,如果我直接调用 requestLayout
上一个孩子,只是孩子被缩放根据父设定的比例系数!
I am using a ScaleGestureDetector
to detect the "pinch to zoom" gesture and change the layout's scaleFactor. Then I force a layout on the custom layout by calling requestLayout
. Unfortunately this doesn't seem to have any effect on its children. The children's onMeasure
& onLayout
are never called even though the parent goes through its measure & layout cycle. But, if I directly call requestLayout
on one of the children, just that child gets scaled according to the scale factor set in the parent!!
看来,除非 requestLayout
专门叫上来看,它实际上并没有再次进行测量本身,而是使用某种类型的缓存。这是从源头code代表认为它说
It seems that unless requestLayout
is exclusively called on a view, it doesn't actually measure itself again and instead uses some kind of cache. This is evident from the source code for view which says
if (mAttachInfo != null && mAttachInfo.mViewRequestingLayout == null) {
// Only trigger request-during-layout logic if this is the view requesting it,
// not the views in its parent hierarchy
ViewRootImpl viewRoot = getViewRootImpl();
if (viewRoot != null && viewRoot.isInLayout()) {
if (!viewRoot.requestLayoutDuringLayout(this)) {
return;
}
}
mAttachInfo.mViewRequestingLayout = this;
}
如何强制孩子们也去衡量自己再次调用 requestLayout
对他们的父母?
推荐答案
这将迫使重新布局视图的儿童(因为鉴于自身的宽度和高度并不需要改变)
This will force relayout the view's children (given that view's own width and height does not need to change)
private static void relayoutChildren(View view) {
view.measure(
View.MeasureSpec.makeMeasureSpec(view.getMeasuredWidth(), View.MeasureSpec.EXACTLY),
View.MeasureSpec.makeMeasureSpec(view.getMeasuredHeight(), View.MeasureSpec.EXACTLY));
view.layout(view.getLeft(), view.getTop(), view.getRight(), view.getBottom());
}
这篇关于在一个ViewGroup中强制进行重新布局,包括其所有的孩子的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!