第1组UI组件:布局管理器

线性布局 LinearLayout

LinearLayout的常用XML属性及相关方法

XML 属性 相关方法 说 明
android:baselineAligned setBaseAligned(boolean) 该属性设为false,将会阻止该布局管理器与它的子元素的基线对齐
android:divider setDividerDrawable(Drawable) 设置垂直布局时两个按钮之间的分隔条
android:gravity setGravity(int) 设置布局管理器内组件的对齐方式。该属性支持top、bottom、left、right、center_vertical、fill_vertical center_horizontal、fill_horizontal、center、fill、clip_vertical、clip_horizontal几个属性值。也可以同时指定多种对齐方式的组合,例如left|center_vertical代表出现在屏幕左边,而且屏幕居中
android:measureWithLargestChild setMeasureWithLargestChildEnabled(boolean) 当该属性为true时,所有带权重的子元素都会具有最大子元素的最小尺寸。
android:orientation setOrientation(int) 设置布局管理器内组件的排列方式,可以设置为horizontal(水平布局)、vertical(垂直排列,默认值)两个值其中之一

LinearLayout子元素支持的常用XML属性及相关方法

XML 属性 相关方法 说 明
android:layout_gravity 指定该子元素在LinearLayout中得对齐方式
android:layout_weight 指定该子元素在LinearLayout中所占的权重

温馨提示

基本上很多布局管理器都提供了相应的LayoutParams内部类,该内部类用于控制他们的子元素支持指定android:layout_gravity属性,该属性设置该子元素在父容器中得对齐方式。与android:layout_gravity相似的属性还有android:gravity属性(一般容器才支持指定该属性),android:gravity属性用于控制它所包含子元素的对齐方式。

定义如下XML布局管理器

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity= "right|center_vertical">
    <Button  android:id="@+id/btn_one" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/bn1"/>
    <Button  android:id="@+id/btn_two" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/bn2"/>
    <Button  android:id="@+id/btn_three" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/bn3"/>
    <Button  android:id="@+id/btn_four" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/bn4"/>
    <Button  android:id="@+id/btn_five" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="@string/bn5"/>
</LinearLayout>

表格布局 TableLayout

每次向TableLayout中添加一个TableRow、该TableRow就是一个表格行,TableRow也是容器,因此它可以不断地添加其他组件,每添加一个子组件该表格就增加一列。
如果直接向TableLayout中添加组件,那么这个组件将直接占用一行。
在表格布局中,列的宽度由该列中最宽的那个单元格决定,整个表格布局的宽度则取决于父容器的宽度(默认总是占满父容器本身)。
在表格布局管理器中,可以为单元格设置如下3种行为方式。

Shrinkable: 如果某个列被设为Shrinkable,那么该列的所有单元格的宽度可被收缩,以保证该表格能适应父容器的宽度。
Stretchable:如果某个列被设为Stretchable,那么该列的所有单元格的宽度可以被拉伸,以保证组件能完全填满表格空余空间。
Collapsed:如果某个列被设为Collapsed,那么该列的所有单元格会被隐藏。

TableLayout的常用XML属性及相关方法

XML 属性 相关方法 说 明
android:collapseColumns setColumnCollapsed(int,boolean) 设置需要被隐藏的列的列序号。多个列序号之间用逗号隔开
android:shrinkColumns setShrinkAllColumns(boolean) 设置允许被收缩的列的列序号。多个列序号之间用逗号隔开
android:stretchColumns setStretchColumns(boolean) 设置允许被拉伸的列的列序号。多个列序号之间用逗号隔开

实例:丰富的表格布局

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="match_parent" android:layout_height="match_parent">
    <!-- 定义第一个表格布局,指定第2列允许收缩,第3列允许拉伸 -->
    <TableLayout android:id="@+id/TableLayout01" android:layout_width="match_parent" android:layout_height="wrap_content" android:shrinkColumns="1" android:stretchColumns="2">
        <!-- 直接添加按钮,它自己会占一行 -->
        <Button android:id="@+id/ok1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="独自一行的按钮"/>
        <!-- 添加一个表格行 -->
        <TableRow>
            <!-- 为该表格行添加三个按钮 -->
            <Button android:id="@+id/ok2" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮"/>
            <Button android:id="@+id/ok3" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="收缩的按钮"/>
            <Button android:id="@+id/ok4" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="拉伸的按钮"/>
        </TableRow>
    </TableLayout>
    <!-- 定义第2个表格布局 ,指定第2列隐藏-->
    <TableLayout android:id="@+id/TableLayout02" android:layout_width="match_parent" android:layout_height="wrap_content" android:collapseColumns="1">
        <!-- 直接添加按钮,它自己会占一行 -->
        <Button android:id="@+id/ok5" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="独自一行的按钮"/>
        <!-- 添加一个表格行 -->
        <TableRow>
            <!-- 为该表格行添加三个按钮 -->
            <Button android:id="@+id/ok6" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮1"/>
            <Button android:id="@+id/ok7" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮2"/>
            <Button android:id="@+id/ok8" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮3"/>
        </TableRow>
    </TableLayout>
    <!-- 定义第3个表格布局,指定第2列和第3列可以被拉伸-->
    <TableLayout  android:id="@+id/TableLayout03" android:layout_width="match_parent" android:layout_height="wrap_content" android:stretchColumns="1,2">
        <!-- 直接添加按钮,它自己会占一行 -->
        <Button  android:id="@+id/ok9" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="独自一行的按钮" />
        <!--定义一个表格行-->
        <TableRow>
        <!-- 为该表格行添加三个按钮 -->
        <Button  android:id="@+id/ok10" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮" />
        <Button  android:id="@+id/ok11" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="拉伸的按钮" />
        <Button  android:id="@+id/ok12" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="拉伸的按钮" />
        </TableRow>
        <!--定义一个表格行-->
        <TableRow>
            <!-- 为该表格行添加两个按钮 -->
            <Button  android:id="@+id/ok13" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="普通按钮" />
            <Button  android:id="@+id/ok14" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="拉伸的按钮" />
        </TableRow>
    </TableLayout>
</LinearLayout>

注意

因为Android推荐将字符串集中放到XML文件中管理,但此处为了编程简单,所以直接在XML布局文件中给出里了按钮文本的字符串。

帧布局 FrameLayout

FrameLayout的常用XML属性及相关方法

XML 属性 相关方法 说 明
android:foreground setForeground(Drawable) 该属该帧布局容器的前景图像
android:foregroundGravity setForegroundGravity(int) 定义绘制前景图像的gravity属性

温馨提示

FrameLayout包含的子元素也受FrameLayout.LayoutParams控制,因此它所包含的子元素也可指定android:layout_gravity属性,该属性控制该子元素在FrameLayout中的对齐方式。

实例:霓虹灯效果

程序清单:main.xml

<?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">
    <!-- 依次定义6个TextView,先定义的TextView位于底层 后定义的TextView位于上层 -->
    <TextView  android:id="@+id/view01" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="160pt" android:height="160pt" android:background="#f00"/>
    <TextView  android:id="@+id/view02" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="140pt" android:height="140pt" android:background="#0f0"/>
    <TextView  android:id="@+id/view03" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="120pt" android:height="120pt" android:background="#00f"/>
    <TextView  android:id="@+id/view04" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="100pt" android:height="100pt" android:background="#ff0"/>
    <TextView  android:id="@+id/view05" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="80pt" android:height="80pt" android:background="#f0f"/>
    <TextView  android:id="@+id/view06" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center" android:width="60pt" android:height="60pt" android:background="#0ff"/>
</FrameLayout>

程序清单:MainActivity.java

package org.yonga.ui;

import android.app.Activity;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.widget.TextView;

import java.util.Timer;
import java.util.TimerTask;

public class MainActivity extends Activity {
    private int currentColor = 0;
    // 定义一个颜色数组
    final int[] colors = new int[] {
        R.color.color1,R.color.color2,R.color.color3,R.color.color4,R.color.color5,R.color.color6
    };
    final int[] names = new int[] {
            R.id.view01,R.id.view02,R.id.view03,R.id.view04,R.id.view05,R.id.view06 };
    TextView[] views = new TextView[names.length];
    Handler handler = new Handler()
    {
        @Override
        public void handleMessage(Message msg)
        {
            // 表明消息来自本程序所发送
            if (msg.what == 0x123)
            {
                for (int i = 0; i < names.length; i++)
                {
                    views[i].setBackgroundResource(colors[(i
                            + currentColor) % names.length]);
                }
                currentColor++;
            }
            super.handleMessage(msg);
        }
    };
    @Override
    public void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        for (int i = 0; i < names.length; i++)
        {
            views[i] = (TextView) findViewById(names[i]);
        }
        // 定义一个线程周期性地改变currentColor变量值
        new Timer().schedule(new TimerTask()
        {
            @Override
            public void run()
            {
                // 发送一条空消息通知系统改变6个TextView组件的背景色
                handler.sendEmptyMessage(0x123);
            }
        },0,200);
    }
}

注意

因为Android的View和UI组件不是线程安全的,所以Android不允许开发者启动线程访问用户界面的UI组件。因此程序中额外定义了一个Handler来处理TextView背景色的更新。

相对布局 RelativeLayout

RelativeLayout的常用XML属性及相关方法

XML 属性 相关方法 说 明
android:gravity setGravity(int) 设置该布局容器内各子组件的对齐方式
android:ignoreGravity setIgnoreGravity(int) 设置哪个组件不受gravity属性的影响

RelativeLayout.LayoutParams里只能设为boolean值的属性

XML 属性 说明
android:layout_centerHorizontal 控制该子组件是否位于布局容器的水平居中
android:layout_centerVertical 控制该子组件是否位于布局容器的垂直居中
android:layout_centerInParent 控制该子组件是否位于布局容器的中央位置
android:layout_alignParentBottom 控制该子组件是否与布局容器底端对齐
android:layout_alignParentLeft 控制该子组件是否与布局容器左边对齐
android:layout_alignParentRight 控制该子组件是否与布局容器右边对齐
android:layout_alignParentTop 控制该子组件是否与布局容器顶端对齐

RelativeLayout.LayoutParams里只能设为设为其他UI组件ID的属性

XML 属性 说明
android:layout_toRightOf 控制该子组件是否位于给出ID组件的右侧
android:layout_toLeftOf 控制该子组件是否位于给出ID组件的左侧
android:layout_above 控制该子组件是否位于给出ID组件的上方
android:layout_below 控制该子组件是否位于给出ID组件的下方
android:layout_alignTop 控制该子组件与给出ID组件的上边界对齐
android:layout_alignBottom 控制该子组件与给出ID组件的下边界对齐
android:layout_alignLeft 控制该子组件与给出ID组件的左边界对齐
android:layout_alignRight 控制该子组件与给出ID组件的右边界对齐

除此之外,RelativeLayout.LayoutParams还继承了android.view.ViewGroup.MarginLayoutParams,因此RelativeLayout布局容器中每个子组件也可以指定android.view.ViewGroup.MarginLayoutParams所支持的各XML属性。

实例:梅花布局效果

<?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">
    <!-- 定义该组件位于父容器中间 -->
    <TextView  android:id="@+id/view01" android:layout_width="wrap_content" android:layout_height="wrap_content" android:background="@drawable/leaf" android:layout_centerInParent="true"/>
    <!-- 定义该组件位于view01组件的上方 -->
    <TextView  android:id="@+id/view02" android:layout_width="wrap_content" android:layout_height="wrap_content" android:background="@drawable/leaf" android:layout_above="@id/view01" android:layout_alignLeft="@id/view01"/>
    <!-- 定义该组件位于view01组件的下方 -->
    <TextView  android:id="@+id/view03" android:layout_width="wrap_content" android:layout_height="wrap_content" android:background="@drawable/leaf" android:layout_below="@id/view01" android:layout_alignLeft="@id/view01"/>
    <!-- 定义该组件位于view01组件的左边 -->
    <TextView  android:id="@+id/view04" android:layout_width="wrap_content" android:layout_height="wrap_content" android:background="@drawable/leaf" android:layout_toLeftOf="@id/view01" android:layout_alignTop="@id/view01"/>
    <!-- 定义该组件位于view01组件的右边 -->
    <TextView  android:id="@+id/view05" android:layout_width="wrap_content" android:layout_height="wrap_content" android:background="@drawable/leaf" android:layout_toRightOf="@id/view01" android:layout_alignTop="@id/view01"/>
</RelativeLayout>

网格布局 GridLayout

GridLayout提供了setRowCount(int)和setColumnCount(int)方法来控制该网格的行数量和列数量。

GridLayout的XML属性及相关方法

XML 属性 相关方法 说明
android:alignmentMode setAlignmentMode(int) 设置该布局管理器采用的对齐模式
android:columnCount setColumnCount(int) 设置该网格的列数量
android:columnOrderPreserved setColumnOrderPreserved(boolean) 设置该网格容器是否保留列序号
android:rowCount setRowCount(int) 设置该网格的行数量
android:rowOrderPreserved setRowOrderPreserved(boolean) 设置该网格容器是否保留行序号
android:useDefaultMargins setUseDefaultMargins(boolean) 设置该布局管理器是否使用默认的页边距

GridLayout.LayoutParams的XML属性及相关方法

XML 属性 相关方法 说明
android:layout_column 设置该子组件在GridLayout的第几列
android:layout_columnSpan 设置该子组件在GridLayout横向上跨几列
android:layout_gravity setGravity(int) 设置该子组件采用何种方式占据该网格的空间
android:layout_row 设置该子组件在GridLayout的第几行
android:layout_rowSpan 设置该子组件在GridLayout纵向上跨几行

实例:计算器界面

1.在布局管理器中定义一个GridLayout,并在该GridLayout中依次定义文本框、按钮各横跨4列。
2.在Java代码中循环16次,依次添加16个按钮。

程序清单:main.xml

<?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:columnCount="4" android:id="@+id/root">
    <!-- 定义一个横跨4列的文本框, 并设置该文本框的前景色、背景色等属性 -->
    <TextView  android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_columnSpan="4" android:textSize="50sp" android:layout_marginLeft="2pt" android:layout_marginRight="2pt" android:padding="3pt" android:layout_gravity="right" android:background="#eee" android:textColor="#000" android:text="0"/>
    <!-- 定义一个横跨4列的按钮 -->
    <Button  android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_columnSpan="4" android:text="清除"/>
</GridLayout>

程序清单:MainActivity.java

package org.yonga.ui;

import android.app.Activity;
import android.os.Bundle;
import android.view.Gravity;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Button;
import android.widget.GridLayout;


public class MainActivity extends Activity {
    GridLayout gridLayout;
    // 定义16个按钮的文本
    String[] chars = new String[]
            {
                    "7","8","9","÷","4","5","6","×","1","2","3","-",".","0","=","+"
            };
    @Override
    public void onCreate(Bundle savedInstanceState)
    {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        gridLayout = (GridLayout) findViewById(R.id.root);
        for(int i = 0 ; i < chars.length ; i++)
        {
            Button bn = new Button(this);
            bn.setText(chars[i]);
            // 设置该按钮的字号大小
            bn.setTextSize(40);
            // 设置按钮四周的空白区域
            bn.setPadding(5,35,5,35);
            // 指定该组件所在的行
            GridLayout.Spec rowSpec = GridLayout.spec(i / 4 + 2);
            // 指定该组件所在的列
            GridLayout.Spec columnSpec = GridLayout.spec(i % 4);
            GridLayout.LayoutParams params = new GridLayout.LayoutParams(
                    rowSpec,columnSpec);
            // 指定该组件占满父容器
            params.setGravity(Gravity.FILL);
            gridLayout.addView(bn,params);
        }
    }
}

相关文章

php输出xml格式字符串
J2ME Mobile 3D入门教程系列文章之一
XML轻松学习手册
XML入门的常见问题(一)
XML入门的常见问题(三)
XML轻松学习手册(2)XML概念