- Include
Include 在积累一些可以复用的layout小模块时是很有用的,比如随着开发的进行,会有一些layout被重复的用到,典型的比如footer,很多需要用户最终选择ok和cancel的activity需要用到,那这个时候include就排上用场了,写一个单独的layout footer,在需要的时候直接include医经写好的footer就可以了,不仅方便,而且使得UI风格一至。
common_footer.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/footer"
android:layout_width="wrap_content"
android:layout_height="wrap_content" >
<Button
android:id="@+id/button1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginRight="5dp"
android:layout_weight="1"
android:text="ok" />
<Button
android:id="@+id/button2"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginLeft="5dp"
android:layout_weight="1"
android:text="cancel" />
</LinearLayout>
main_activity.xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.androiddemos.LayoutDemoActivity" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" />
<include
android:id="@+id/footer_ref"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
layout="@layout/common_footer" />
</RelativeLayout>
需要注意的一定,在include里可以复写include_*的属性,前提是必须复写layout_width和layout_height的情况下才会起作用。
这样小模块积累的越来越多,开发也会越来月顺利。
2. merge
merge 是用来消除多余的layout节点,减少layout的层次时用到的,众所周知,layout的层次越小,UI就会越流畅,特别是在使用listView需要重复的画Ui的时候,用hieararchyviewer查看自己UI的结构,去除多余的layout,是优化layout的一个不错的方法。
像上面那样,我们需要引用的footer是放在Linearlayout里的,而我们的footer是放在RelativeLayout里的。想象另外一种情况,如果我们想要引用的模块是一个LinearLayout,而我们正好也要把这个模块放到另一个LinearLayout里,那么,我们可能就不需要使用两个LinearLayout,我们就可以把模块的LinearLayout改为merge,而省去一个layout层次。
merge_layout.xml
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" >
<Button
android:id="@+id/button1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Button" />
<Button
android:id="@+id/button2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Button" />
</merge>
main_activity.xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context="${relativePackage}.${activityClass}" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" />
<include
android:layout_width="wrap_content"
android:layout_height="wrap_content"
layout="@layout/merge_layout" />
</LinearLayout>
3. ViewStub
在有些时候,一些view并不是每一次都需要画出来,或者说,很少才会画出来。比如一些错误提示的view,一些在第一次运行才会出现的提示的view,那这些view如果一直在layout里未免影响性能。这里用ViewStub会是一个不错的选择,轻量级,大小为0,不需要画,也不参与layout,仅在需要的时候才画出来。
借用刚才用过的footer做一个demo
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context="${relativePackage}.${activityClass}" >
<ViewStub
android:id="@+id/stub"
android:inflatedId="@+id/panel_import"
android:layout="@layout/common_footer"
android:layout_width="match_parent"
android:layout_height="wrap_content"/>
</LinearLayout>
findViewById(R.id.stub).setVisibility(View.VISIBLE);
//或者
View importPanel = ((ViewStub) findViewById(R.id.stub)).inflate();
这个时候ViewStub的位置就会被其指定的layout common_footer所代替
参考