我有一个视图的XML定义,我将使用addChild添加到更大的容器视图中。它基于LinearLayout
,看起来基本上是这样的:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="52dip"
android:background="@drawable/box_bg"
android:clickable="true"
android:onClick="onTreeBoxClick"
android:orientation="horizontal" >
<ImageView android:id="@+id/box_photo"
android:layout_width="45dip"
android:layout_height="45dip"
...
/>
<RelativeLayout
android:layout_width="0dip"
android:layout_weight="1"
android:layout_height="wrap_content"
>
(省略剩余 - 可能不相关,因为它基本上按设计工作)
当我创建这些视图时,我发现以下对我来说很奇怪的行为:
在我给视图充气后,getLayoutParameters()返回null。
在我调用addChild()将其添加到其父级后,getLayoutParameters()返回一个有效的对象。
检查LayoutParameters,我发现宽度和高度都设置为-2(WRAP_CONTENT),这显然不是我在XML文件中指定的。
当我查看随附的ImageView的布局参数时,它会以指定的值读出。
任何人都可以解释这里发生了什么吗?为什么我的指定高度没有被注意到?
这并没有真正影响我,因为父视图是一个自定义视图,其中我使用MeasureSpec等强制子项的最终尺寸,但我还是要理解这一点!
答案 0 :(得分:22)
您没有提供一些重要的细节。
1)在我给视图充气后,getLayoutParameters()返回null。
我认为你用过这个:
inflater.inflate(R.layout.content, null);
在这种情况下,LayoutInflater
无法为根LayoutParams
制作(根本)正确的Linearlayout
,因为它不知道谁将成为其父级(因此它可以创建正确类型的LayoutParams
)。如果你愿意的话:
inflater.inflate(R.layout.content, someOtherLayout, false/true);
然后根LinearLayout
将具有正确的LayoutParams
,因为它会看到someOtherLayout
的类型,并根据此信息创建LayoutParams
。如果这不是您目前所做的,那么您可能需要提供一段代码以获得更好的答案。
2)在我调用addChild()将其添加到其父级之后 getLayoutParameters()返回一个有效的对象。
我假设您谈论addView()
方法。 addView()
方法会检查尝试添加的视图的LayoutParams
,如果这些LayoutParams
为null
,则会自动为该视图分配LayoutParams
其generateDefaultLayoutParams()
方法返回的对象。
3)检查LayoutParameters,我发现宽度和高度都设置为 -2(WRAP_CONTENT),这显然不是我在XML文件中指定的。
正如我在2处所说的那样,生成的LayoutParams
来自generateDefaultLayoutParams()
方法,它将返回LayoutParams
实例,就像父设计的那样。例如,方向为LinearLayout
的{{1}}(默认值为1)将返回宽度/高度设置为HORIZONTAL
的{{1}}个实例。
4)当我查看随附的ImageView的布局参数时,它 读出指定的值。
因为LayoutParams
处理了这个问题,因为WRAP_CONTENT
位于布局的内部,并且有一个已知的父级LayoutInflater
可以使ImageView
正确LayoutInflater
}。