学习Android从0开始之基础篇(3)-视图组件之布局管理器

最后更新于:2022-04-01 11:26:25

## Android布局管理器 **Android的Activity**组件通过setContentView(xml resId) 来为activity绑定显示界面,然而为了更好的更方便的管理Android应用的用户界面里面的各种控件(按钮  文本框  编辑框 图片等一系列组件),Android向我们提供了布局管理器。通过使用布局管理器,Android的图形界面跟java代码间具有很好 的 无关性,使代码与布局分开,这样就能减少代码量,代码只需要做一些界面组件的控制和一些数据处理,这样就有点类似java 中的MVC( modle    view    control)结构,android中的布局管理器就起到了View的作用,而java代码就起到了control的作用,android中的数据存储就起到了modle的作用。介绍完了布局管理器是什么了以后,接下来就介绍布局管理器有哪几类,布局管理器有:线性布局(LinearLayout)   相对布局(RelativeLayout)  网格布局(GridLayout) 帧布局(FrameLayout)  绝对布局(AbsoluteLayout)   接下来一一介绍各种布局管理器的作用。   1. **线性布局(LinearLayout)** 首先来到官方文档,看看官方文档的介绍(一定要会看官方文档)如下 ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c617953.jpg) 官方大意为:在一个单一的列或一行排列其子的布局。该行的方向可以通过调用setorientation()来设置水平还是垂直。你也可以指定排列方式,通过设置LinearLayout.layoutparams来指定所排列的所有子元素调用setgravity()或指定特定的孩子的权重来填补剩余的空间布局。默认方向为水平。  还有一点非常重要,那就是LinearLayout中的组件排列起来的沿排列方向超出了屏幕的宽度,多出的部分是不会显示出来的。 再来看看LinearLayout的XML属性及相关方法,如下表:官方文档 ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c62b14d.jpg) 接下来就跟着官方文档的属性介绍单个详细介绍: ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c66e302.jpg) 该属性设置为false,将会阻止该布局管理器与它的子元素的基线对齐。当它的子元素使用不同的权重值时这个熟悉特别有用,默认是true。 必须是Boolean值,是true或者false; ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c683835.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c698e71.jpg)               设置垂直布局时两个按钮之间的分割条 ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c6ae8a9.jpg) 设置布局管理器内组件的对齐方式,该属性支持top、bottom、left、right、center_vertical、fill_vertical、center_horizoontal、fill_horizontal、center、fill、clip_vertical、clip_horizontal这几个属性值,也可以同时指定多种组合,比如:left | center_vertical 代表的是出现在屏幕的左边,而且垂直居中; ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c6cb9bd.jpg) 当该属性设置为true时,所有带权重的子元素都会具有最大子元素的最小尺寸 ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c6e21ba.jpg) 设置布局管理器内部组件的排列方式,可以设置为horizontal(水平)、vertical(垂直)之一,默认是vertical; ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7024d8.jpg) 在LinearLayout的XML中,举个例子:android:weightSum="5" 表示这个LinearLayout总共平分成5块大小区域;然后再LinearLayout里面的控件,使用android:layout_wetght=“1”,这表示它占用整个布局的1/5。 通过介绍了上面LinearLayout的属性后,我们在通过下面的几个例子来展示这个几个属性的使用: ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c714dba.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7311d8.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c74e528.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c76880f.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7847a9.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7a3857.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7c335b.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7dedc8.jpg) ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c7dedc8.jpg) 通过上面几个例子的展示,可以很只管的了解LinearLayout的那几个属性的使用效果。 2. 相对布局 (RelativeLayout) 通过Linearlayout的官方文档介绍方法,大家可以上Android官网去查看,就按照上面的步骤学习其他组件。后面几个布局管理器就不以上面的方式讲解,就直接以简短明了的方式向大家介绍。 相对布局容器内部的子组件的位置总是相对兄弟组件、父容器来决定的,因此这种布局方式被称之为相对布局,例如:如果B组件的位置要由A组件的位置来决定的话,那么就必须先定义B组件并且,确定B的位置后,才能定义A组件。 RelativeLayout的XML属性及相关方法说明 <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="left">      XML属性</p></td><td valign="top"><p align="left">      Java方法</p></td><td valign="top"><p align="left">       说明</p></td></tr><tr><td valign="top"><p align="left"><span><span style="font-size:14px">android:gravity</span></span></p></td><td valign="top"><p align="left">setGravity(int)</p></td><td valign="top"><p align="left">设置该布局容器内各子组件的对齐方式</p></td></tr><tr><td valign="top"><p align="left">Android:ignoreGravity</p></td><td valign="top"><p align="left">setIgnoreGravity(int)</p></td><td valign="top"><p align="left">设置哪个组件不收gravity属性影响</p></td></tr></tbody></table> 为了能够控制该布局容器中各个子组件的布局分布,Relative也提供了一个内部类:RelativeLayout.LayoutParams,该类提供了大量的XML属性来控制Relative布局容器中子组件的布局分布,它的xml属性如下表所示: 下面的值只能是true或false <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="left">android:layout_centerHorizontal</p></td><td valign="top"><p align="left">控制该子组件是否位于布局容器的水平居中</p></td></tr><tr><td valign="top"><p align="left">android:layout_centerVertical</p></td><td valign="top"><p align="left">控制该子组件是否位于布局容器的垂直居中</p></td></tr><tr><td valign="top"><p align="left">android:layout_centerInparent</p></td><td valign="top"><p align="left">控制该子组件是否位于布局容器的中央位置</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignParentBottom</p></td><td valign="top"><p align="left">控制该子组件是否于布局容器底部对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignParentLeft</p></td><td valign="top"><p align="left">控制该子组件是否于布局容器左边对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignParentRight</p></td><td valign="top"><p align="left">控制该子组件是否于布局容器右边对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignParentTop</p></td><td valign="top"><p align="left">控制该子组件是否于布局容器顶端对齐</p></td></tr></tbody></table> 下面的属性的值只能是其他UI组件的id值 <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="left">android:layout_toRightOf</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的右侧</p></td></tr><tr><td valign="top"><p align="left">android:layout_toLeftOf</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的左侧</p></td></tr><tr><td valign="top"><p align="left">android:layout_above</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的上方</p></td></tr><tr><td valign="top"><p align="left">android:layout_below</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件下方</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignTop</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的上边界对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignBottom</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的下边界对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignLeft</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的左边界对齐</p></td></tr><tr><td valign="top"><p align="left">android:layout_alignRight</p></td><td valign="top"><p align="left">控制该子组件位于给出id组件的右边界对齐</p></td></tr></tbody></table>   下面是通过一个雪花效果来展示Relative的具体使用效果 ~~~ <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:background="#000000"> <!--定义该组件位于父容器的中央--> <TextView android:id="@+id/xuehua_1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_centerInParent="true" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于view1的上方--> <TextView android:id="@+id/xuehua_2" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_above="@id/xuehua_1" android:layout_alignLeft="@id/xuehua_1" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于view1的下方--> <TextView android:id="@+id/xuehua_3" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignLeft="@id/xuehua_1" android:layout_below="@id/xuehua_1" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于view1的左方--> <TextView android:id="@+id/xuehua_4" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignTop="@id/xuehua_1" android:layout_toLeftOf="@id/xuehua_1" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于view1的右方--> <TextView android:id="@+id/xuehua_5" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignTop="@id/xuehua_1" android:layout_toRightOf="@id/xuehua_1" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于父容器的上方中央--> <TextView android:id="@+id/xuehua_6" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentTop="true" android:layout_centerHorizontal="true" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于父容器的左边中央--> <TextView android:id="@+id/xuehua_7" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:layout_centerVertical="true" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于父容器的右边中央--> <TextView android:id="@+id/xuehua_8" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_centerVertical="true" android:background="@drawable/iconfont_xuehua" /> <!--定义该组件位于父容器的下边居中--> <TextView android:id="@+id/xuehua_9" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentBottom="true" android:layout_centerHorizontal="true" android:background="@drawable/iconfont_xuehua" /> </RelativeLayout> ~~~ 下面是效果图: ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c811b00.jpg) 3. **网格布局(GridLayout)** **网格布局是 Android4.0以后新推出的布局管理器,顾名思义,网格布局就是把整个容器划分为rows X columns个网格,每个网格放一个组件,除此之外还可以设置一个组件横跨多少列、一个组件纵跨多少行。gridlayout的xml属性和相关方法如下:** **** <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="left">Xml属性</p></td><td valign="top"><p align="left">相关方法</p></td><td valign="top"><p align="left">说明</p></td></tr><tr><td valign="top"><p align="left">Andorid:alignmentMode</p></td><td valign="top"><p align="left">setAlignmentMode(int)</p></td><td valign="top"><p align="left">设置该布局管理器采用的对齐方式</p></td></tr><tr><td valign="top"><p align="left">Android:columnCount</p></td><td valign="top"><p align="left">setColumnCount(int)</p></td><td valign="top"><p align="left">设置该网格的列数量</p></td></tr><tr><td valign="top"><p align="left">Android:columnOrderPreserved</p></td><td valign="top"><p align="left">setColumnOrderPreserved(boolean)</p></td><td valign="top"><p align="left">设置该网格空容器是否保留列序号</p></td></tr><tr><td valign="top"><p align="left">Android:rowCount</p></td><td valign="top"><p align="left">setRowCount(int)</p></td><td valign="top"><p align="left">设置该网格的行数量</p></td></tr><tr><td valign="top"><p align="left">Android:rowOrderPreserved</p></td><td valign="top"><p align="left">setRowOrderPreserved(boolean)</p></td><td valign="top"><p align="left">设置该网格容器是否保留行序号</p></td></tr><tr><td valign="top"><p align="left">Androi:useDefaultMargins</p></td><td valign="top"><p align="left">setDefaultMargins(boolean)</p></td><td valign="top"><p align="left">设置该布局管理器是否使用默认的页边距</p></td></tr></tbody></table>     为了控制GridLayout布局容器中各子组件的布局分布,GridLayout也提供了一个内部类:GridLayouut.Params,该类提供了大量的XML属性来控制GridLayout布局容器中子组件的布局分布。        GridLayout.LayoutParams的XML属性   <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="center">Xml属性</p></td><td valign="top"><p align="center">相关方法</p></td><td valign="top"><p align="center">说明</p></td></tr><tr><td valign="top"><p align="center">Android:layout_column</p></td><td valign="top"><p align="center"> </p></td><td valign="top"><p align="center">设置该子组件在GridLayout的第几列</p></td></tr><tr><td valign="top"><p align="center">Android:layout_columSpan</p></td><td valign="top"><p align="center"> </p></td><td valign="top"><p align="center">设置该子组件在GridLayout横向上跨几列</p></td></tr><tr><td valign="top"><p align="center">Android:layout_gravity</p></td><td valign="top"><p align="center">setGravity(int)</p></td><td valign="top"><p align="center">设置该子组件采用何种方式占据该网格的空间</p></td></tr><tr><td valign="top"><p align="center">Android:layout_row</p></td><td valign="top"><p align="center"> </p></td><td valign="top"><p align="center">设置该子组件在GridLayout的第几行</p></td></tr><tr><td valign="top"><p align="center">Android:layout_rowSpan</p></td><td valign="top"><p align="center"> </p></td><td valign="top"><p align="center">设置该子组件在GridLayout纵向上跨几行</p></td></tr></tbody></table>                          下面以计算器为例来讲解GridLayout的使用: ~~~ <?xml version="1.0" encoding="utf-8"?> <GridLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:rowCount="6" android:background="#000" android:columnCount="4"> <!--定义一个横跨4列的文本框--> <TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_columnSpan="4" android:layout_marginLeft="10dp" android:layout_marginRight="10dp" android:padding="5dp" android:layout_gravity="right" android:background="#EEEEEE" android:textColor="#000" android:text="0" android:singleLine="true" android:textSize="50sp"/> <!--定义一个横跨4列的按钮--> <Button android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_columnSpan="4" android:text="清除" android:textSize="22sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="7" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="8" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="9" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="/" android:layout_gravity="fill" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="4" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="5" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="6" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="*" android:layout_gravity="fill" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="1" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="2" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="3" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="-" android:layout_gravity="fill" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="." android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="0" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="=" android:textSize="20sp"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="+" android:layout_gravity="fill_horizontal" android:textSize="20sp"/> </GridLayout> ~~~      效果图如下: ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c826e7d.jpg) 4. 帧布局(FramLayout) 帧布局为为每个加入其中的组件创建一个空白的区域,称为一帧,每个子组件各占据一帧,然而这些组件都会根据grivaty属性执行自动对齐。其实可以理解为堆扑克牌一样,一张一张的堆在一起,上面的一张卡片放在下面一张卡片上面。 FrameLayout的常用属性及相关方法 <table border="1" cellspacing="0" cellpadding="0"><tbody><tr><td valign="top"><p align="center">Xml属性</p></td><td valign="top"><p align="center">相关方法</p></td><td valign="top"><p align="center">说明</p></td></tr><tr><td valign="top"><p align="center">Android:foreground</p></td><td valign="top"><p align="center">setForeground(Drawable)</p></td><td valign="top"><p align="center">设置该帧布局容器的前景图像</p></td></tr><tr><td valign="top"><p align="center">Android:foregroundGravity</p></td><td valign="top"><p align="center">setForegroundGravity(int)</p></td><td valign="top"><p align="center">定义绘制前景图像的gravity属性</p></td></tr></tbody></table> ~~~ <?xml version="1.0" encoding="utf-8"?> <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="300dp" android:height="300dp" android:background="#f00"/> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="200dp" android:height="200dp" android:background="#0f0"/> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="100dp" android:height="100dp" android:background="#00f"/> </FrameLayout> ~~~ 效果图如下: ![](https://docs.gechiui.com/gc-content/uploads/sites/kancloud/2016-04-26_571f42c83b57a.jpg) **5. 绝对布局(AbsoluteLayout)** 绝对布局通过直接设置组件的X  、Y坐标来设置组件的位置,然而布局管理器将不会管理子组件的位置和大小,完全有开发人员设置。但是,使用绝对布局来控制子组件的大小是一个不太推荐的思路,因为市面上运行Android系统的手机差距相差万别,它们的屏幕大小、分辨率都很不同,使用绝对布局是不可能做到各种屏幕上面显示效果都一样。因此AbsoluteLayout不觉管理器已经不适合在项目中使用了。
';