我想知道LayoutParams
如何在LayoutInflator
上运作。以下是什么区别:
LinearLayout childLayout=(LinearLayout)inflater.inflate(R.layout.childitemlayout, null); //FIRST WAY
LinearLayout childLayout=(LinearLayout)inflater.inflate(R.layout.childitemlayout, container,false); //SECOND WAY
因为,这两种方法都给我不同的结果。 实际上第二次充气方法给了我两个子布局改变的正确结果,但是第一种方法会给我不同的结果。
这是我的代码:
MainActivity.Java
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
LinearLayout mainLayout=(LinearLayout)findViewById(R.id.mainLayout);
LayoutInflater inflater=LayoutInflater.from(getApplicationContext());
for(int i=0;i<10;i++){
LinearLayout childLayout=(LinearLayout)inflater.inflate(R.layout.childitemlayout, null); //First WAY
// LinearLayout childLayout=(LinearLayout)inflater.inflate(R.layout.childitemlayout, mainLayout,false); //SECOND WAY
mainLayout.addView(childLayout);
}
}
main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/mainLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="horizontal" >
</LinearLayout>
childitemlayout.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="80dp"
android:layout_height="80dp"
android:orientation="vertical"
android:background="#525f67">
<TextView android:id="@+id/btn"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:text="Button"
android:gravity="center"
/>
</LinearLayout> <!-- Both ways gives different result -->
<!--
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
android:background="#525f67">
<TextView android:id="@+id/btn"
android:layout_width="80dp"
android:layout_height="80dp"
android:text="Button"
android:gravity="center"
/>
</LinearLayout> Both method gives SAME result -->
答案 0 :(得分:12)
两个inflate()
方法之间的主要区别是第二个参数(ViewGroup
参数)及其用于为膨胀的布局文件的根视图设置正确的LayoutParams
。这很重要,因为LayoutParams
保留了视图的各种布局属性(如宽度,高度,定位规则等),并且是必需的,因此该视图的父级可以正确显示视图。
第一种方法基本上说:从这个布局文件构建层次结构视图,但不要将LayoutParams
分配给膨胀层次结构的根(可能因为父级还不知道),不要将膨胀的视图附加到父。
第二个inflate方法说:从此布局文件构建层次结构视图,还将适当的LayoutParams
(基于给予inflate方法的第二个参数)分配给根目录。膨胀的层次结构,也不要将膨胀的视图附加到父。
在第一种情况下,膨胀的布局文件(R.layout.childitemlayout
)的根将不会设置任何LayoutParams
(inflate
方法没有分配任何因为第二个参数是null
,它不知道要生成哪种类型的LayoutParams
,因此您的固定宽度/高度值会丢失。稍后当您mainLayout.addView(childLayout);
时,mainLayout
会检查LayoutParams
的{{1}},看看它们是childLayout
,并会自动设置null
(使用其LayoutParams
方法)。在水平generateDefaultLayoutParams()
的特定情况下,此方法将返回LinearLayout
的实例,其中宽度/高度将设置为LayoutParams
。因此,WRAP_CONTENT
最终会以childLayout
作为其大小,而不是您在其上设置的固定值。
在第二种情况下,WRAP_CONTENT
方法会看到您将inflate
LinearLayout
建议为用于生成mainLayout
的{{1}}。这意味着从布局文件中检索的固定值(用于宽度/高度)可以存储在ViewGroup
的适当实例中。当您执行LayoutParams
时,LayoutParams
会看到mainLayout.addView(childLayout);
具有正确的mainLayout
实例(其中包含布局文件中使用的值)并且不会调用它childLayout
。