Android之layout_weight解析

我们先来看以下这段Android布局代码:

 1 <LinearLayout
 2     xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent">
 5 
 6     <TextView
 7         android:layout_width="0.0dip"
 8         android:layout_height="100.0dip"
 9         android:layout_weight="1"
10         android:background="@color/colorAccent"
11         android:gravity="center"
12         android:text="1111111111111111111"
13         android:textColor="@color/black"
14         android:textSize="18.0sp"
15         android:textStyle="bold"/>
16 
17     <TextView
18         android:layout_width="0.0dip"
19         android:layout_height="100.0dip"
20         android:layout_weight="2"
21         android:background="@color/colorPrimary"
22         android:gravity="center"
23         android:text="2"
24         android:textColor="@color/black"
25         android:textSize="18.0sp"
26         android:textStyle="bold"/>
27 
28     <TextView
29         android:layout_width="0.0dip"
30         android:layout_height="100.0dip"
31         android:layout_weight="3"
32         android:background="@color/white"
33         android:gravity="center"
34         android:text="3"
35         android:textColor="@color/black"
36         android:textSize="18.0sp"
37         android:textStyle="bold"/>
38 
39 </LinearLayout>
layout_weight解析一代码

在线性布局LinearLayout中,三个TextView以layout_weight属性分别是1、2、3来布局,它们的高度都是100dip,宽度都是0dip。在这种情况下,三个TextView的布局是什么样子的呢?答案如下图所示。

如上图所示,三个TextView所占的宽度分别是1:2:3,这是在我们意料之中的,在我们意料之外的是,第一个TextView的位置偏下。这是为什么呢?我们只需要对结果图稍作处理,答案就会显而易见,见下图。

如上图所示,我们加上一道“辅助线”之后就会发现,虽然位置参差不齐,但它们的第一行文本的位置是在同一高度的。由此我们得出结论:在Android的LinearLayout布局中,TextView默认是根据第一行文本来对齐的。可是我们怎样消去这种文本对齐关系呢?我们只需要在父布局的LinearLayout中添加这样一句代码 android:baselineAligned="false" 就可以解决这个问题,解决后的布局图如下:

如果我们把某一个TextView的layout_width属性设置为wrap_content,结果又会如何呢?如果我们将上面的布局代码修改成如下的样子,那么我们会得到如下图所示的结果。

 1 <LinearLayout
 2     xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent"
 5     android:baselineAligned="false">
 6 
 7     <TextView
 8         android:layout_width="wrap_content"
 9         android:layout_height="100.0dip"
10         android:layout_weight="1"
11         android:background="@color/colorAccent"
12         android:gravity="center"
13         android:text="1111111111111111111"
14         android:textColor="@color/black"
15         android:textSize="18.0sp"
16         android:textStyle="bold"/>
17 
18     <TextView
19         android:layout_width="0.0dip"
20         android:layout_height="100.0dip"
21         android:layout_weight="2"
22         android:background="@color/colorPrimary"
23         android:gravity="center"
24         android:text="2"
25         android:textColor="@color/black"
26         android:textSize="18.0sp"
27         android:textStyle="bold"/>
28 
29     <TextView
30         android:layout_width="0.0dip"
31         android:layout_height="100.0dip"
32         android:layout_weight="3"
33         android:background="@color/white"
34         android:gravity="center"
35         android:text="3"
36         android:textColor="@color/black"
37         android:textSize="18.0sp"
38         android:textStyle="bold"/>
39 
40 </LinearLayout>
layout_weight解析二代码

我们把第一个TextView的宽度属性设置成wrap_content,结果如上图所示。从结果中我们可以看到,我们得到的结果不符合1:2:3的布局比例。这时为什么呢?这时因为,Android会先分配已经声明尺寸的控件的空间,再分配未声明尺寸的控件的空间。在这个例子中,第一个TextView的宽度已经声明(wrap_content),而另外两个TextView的宽度都是0(等待父布局按layout_weight分配),那么Android就会先分配第一个TextView的空间,然后再把剩余的空间按1:2:3的比例分配给三个TextView。

如果三个TextView的宽度都是已经声明的,结果又会是怎样的呢?我们把三个TextView的宽度比例改成1:2:2,并把它们的宽度都设置成match_parent(代码如下),这样,我们就会得到如下图所示的结果。

 1 <LinearLayout
 2     xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent"
 5     android:baselineAligned="false">
 6 
 7     <TextView
 8         android:layout_width="match_parent"
 9         android:layout_height="100.0dip"
10         android:layout_weight="1"
11         android:background="@color/colorAccent"
12         android:gravity="center"
13         android:text="1111111111111111111"
14         android:textColor="@color/black"
15         android:textSize="18.0sp"
16         android:textStyle="bold"/>
17 
18     <TextView
19         android:layout_width="match_parent"
20         android:layout_height="100.0dip"
21         android:layout_weight="2"
22         android:background="@color/colorPrimary"
23         android:gravity="center"
24         android:text="2"
25         android:textColor="@color/black"
26         android:textSize="18.0sp"
27         android:textStyle="bold"/>
28 
29     <TextView
30         android:layout_width="match_parent"
31         android:layout_height="100.0dip"
32         android:layout_weight="2"
33         android:background="@color/white"
34         android:gravity="center"
35         android:text="3"
36         android:textColor="@color/black"
37         android:textSize="18.0sp"
38         android:textStyle="bold"/>
39 
40 </LinearLayout>
layout_weight解析三代码

按照我们上一个demo得到的结论,Android先分配已经声明的控件的空间,那么这里,这三个TextView的宽度应该是按照1:2:2的比例分配的,即把屏幕宽度分成五份,然后让这三个TextView分别占一份、两份、两份。但现在为什么得到的结果与理论不相同呢?其实,我们得到的结果正是“一丝不苟”的按照我们得到的理论进行的,下面我们来分析一下。

我们假设手机屏幕的宽度是480dip,那么按照我们之前得出的结论(先给已经声明的控件分配空间),这三个TextView的宽度都应该是480dip(和屏幕的尺寸相同),那么剩余的空间就是480-(480*3)=-960,也就是说,我们要把-960dip评分成五份,然后按照1:2:2的比例分配给三个TextView。那么,第一个TextView就会分配到-192dip,第二个和第三个TextView都分配到-384dip。用它们之前分配的和屏幕同样宽度的480dip分别减去它们后来分配的尺寸,就可以求出它们实际所占的尺寸分别是288dip、96dip和96dip,即3:1:1。

layout_weight还有一个非常有用的作用,我们来看下面这个需求:我们想要得到一个占屏幕二分之一的TextView,我们该怎么办呢?这时,我们就可以利用layout_weight来解决这个问题。代码如下,结果如下图所示。

 1 <LinearLayout
 2     xmlns:android="http://schemas.android.com/apk/res/android"
 3     android:layout_width="match_parent"
 4     android:layout_height="match_parent"
 5     android:weightSum="2">
 6 
 7     <TextView
 8         android:layout_width="0.0dip"
 9         android:layout_height="100.0dip"
10         android:layout_weight="1"
11         android:background="@color/colorAccent"
12         android:gravity="center"
13         android:text="1111111111111111111"
14         android:textColor="@color/black"
15         android:textSize="18.0sp"
16         android:textStyle="bold"/>
17 
18 </LinearLayout>
layout_weight的另一个作用

posted @ 2016-02-21 20:23  小挂坠  阅读(231)  评论(0编辑  收藏  举报