3.创建高效的layout
Android UI提供了一些layout 管理,这样我们使用起来非常方便,大多数情况下,我们只需要使用一些基本的特性.
但在有些情况下使用这些layout不当会降低layout的效率,滥用LinearLayout会导致视图继承表中视图的臃肿,每一个视图或者layout在添加到应用程序中的时候都会带来一定的性能损耗,这样会导致视图初始化,布局,重绘速度降低.当你在里面又添加了许多的LinearLayout,并且使用了weight属性,你的视图速度将会更慢,因为这样会导致你的孩子节点被测量两次.
让我考虑一个简单而又常用的layout的例子:一个listview,其中左边是一个imageview,一个title在顶部,在title下部是一个可选的description .布局图如下:
为了清楚的理解有哪些视图,我们用以下图来描述:
考虑以下一段使用LinearLayout进行布局的例子:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="?android:attr/listPreferredItemHeight"
android:padding="6dip">
<ImageView
android:id="@+id/icon"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_marginRight="6dip"
android:src="@drawable/icon" />
<LinearLayout
android:orientation="vertical"
android:layout_width="0dip"
android:layout_weight="1"
android:layout_height="fill_parent">
<TextView
android:layout_width="fill_parent"
android:layout_height="0dip"
android:layout_weight="1"
android:gravity="center_vertical"
android:text="My Application" />
<TextView
android:layout_width="fill_parent"
android:layout_height="0dip"
android:layout_weight="1"
android:singleLine="true"
android:ellipsize="marquee"
android:text="Simple application that shows how to use RelativeLayout" />
</LinearLayout>
</LinearLayout>
以上布局可以正常显示,但是当listview对每个item进行实例化的时候会造成资源的很大浪费,我们通过使用 RelativeLayout进行简化:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="?android:attr/listPreferredItemHeight"
android:padding="6dip">
<ImageView
android:id="@+id/icon"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_alignParentTop="true"
android:layout_alignParentBottom="true"
android:layout_marginRight="6dip"
android:src="@drawable/icon" />
<TextView
android:id="@+id/secondLine"
android:layout_width="fill_parent"
android:layout_height="26dip"
android:layout_toRightOf="@id/icon"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:singleLine="true"
android:ellipsize="marquee"
android:text="Simple application that shows how to use RelativeLayout" />
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_toRightOf="@id/icon"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_above="@id/secondLine"
android:layout_alignWithParentIfMissing="true"
android:gravity="center_vertical"
android:text="My Application" />
</RelativeLayout>
以上的代码基本上可以实现之前代码相同的功能,除了一种情况:如果我们不需要显示下面的那一行textview时,如果在LinearLayout中可以简单的将textview的属性设置为gone,但这个属性在RelativeLayout中并不生效.
在RelativeLayout中,一个view可以与它的父类对齐,也可以与RelativeLayout对齐或是其他view.例如,我们如果定义description 与RelativeLayout的底部对齐,title位于描述字段的顶部,与RelativeLayout的顶部对齐,如果description 被设置为GONE,那么title不知道在哪里放置自己的bottom位置了.为了解决这个问题,我们可以使用一个很特别的layout属性layout_alignWithParentIfMissing
如果被参照的目标丢失后,这个boolean 类型的参数通知RelativeLayout使用自己的边缘来作为参照对象.
这样我们的问题就解决了,看一下HierarchyViewer中使用两种layout的区别吧: