第5 章 UI 组件与布局 第4章介绍了Activity,以及Android应用程序中与用户交互的基本单元。一个 Activity中通常包含各种UI控件,以完成不同的功能。这些控件按照一定的位置分布在 Activity的不同区域,这称为布局(layout)。第2 章和第4 章已经使用了Button、 TextView 等控件,以及最简单的布局———LinearLayout(线性布局)。本章将介绍 Android应用程序开发中常用的UI组件和布局。 5.1 常用控件 Android中有多种编写程序界面的方式可供选择。AndroidStudio和Eclipse中都 提供了可视化的界面编辑器。可视化编辑器允许使用拖曳控件的方式对布局进行编辑, 并能在视图上直接修改控件的属性,但是这种方式并不利于真正了解界面背后的原理和 技术。本节在讲解UI组件和布局时,大多数都采用编写XML代码的方式。 下面从Android系统中几种最常见的控件开始熟悉UI组件。 Android提供了大量的UI控件,合理使用这些控件能轻松地编写出美观的界面。本 节将选择几种最常用的控件,详细介绍其使用方法。 Android控件继承结构如图5.1所示。 从图5.1可以看出,View 是Android所有控件的基类,同时ViewGroup也继承自 View。知道View的层级关系有助于理解View。从图5.1可以发现常用的控件都继承 自View,如果掌握了View的知识体系,那么在界面编程时会更加得心应手。 5.1.1 View 类 可以看到,所有的UI控件(主要在包android.view 和包android.widget中)都是 View的子类。使用较早的Android版本进行应用程序开发时,每当用findViewById(R. id.xx)方法时,总要将其返回类型进行强制类型转换,因为该方法返回的是一个View 实 例。其中不得不提View的子类———ViewGroup。Android系统中的所有UI类都建立在 View和ViewGroup 类的基础上。所有View 的子类都称为Widget(小部件),所有 ViewGroup的子类都称为Layout(布局)。View和ViewGroup之间采用组合设计模式, 可以使得“部分-整体”同等对待。ViewGroup作为布局容器类的最上层,布局容器里又 可以有View和ViewGroup。通过这种方式,获得了UI的组合方式。 ViewGroup的子类用不同的方式管理容器中View 控件的摆放位置以及显示方式; 99 第 5 章 UI 组件与布局 但是,对于UI控件具体摆放到什么位置,以及大小等属性,则需要每个布局类的内部类 LayoutParams进行处理,该类是ViewGroup的内部类。LayoutParams类有多个子类实 现,用于指定不同的布局参数。 图5.1 Android控件继承结构 可以看到,Android中所有的UI控件都是View的子类,所以可以通过继承View类 实现自定义控件。注意,此时需要重载View的构造函数。View的构造方法有下面4 个,比较常用的是第一个和第二个。 .publicView(Contextcontext); .publicView(Contextcontext,AtributeSetatrs); .publicView(Contextcontext,AtributeSetatrs,intdefStyleAtr); .publicView(Contextcontext,AtributeSetatrs,intdefStyleAtr,intdefStyleRes); 第一个构造方法的参数context代表该View对象所属的Context对象。第二个构 造方法的参数atrs代表在布局文件中该View对象对应的元素相关的属性值的集合。 使用UI控件时,一般采用下面的步骤。 (1)在布局文件中添加该UI控件的元素(元素的名称与该UI控件的类名完全相 同),并定义该元素的一些属性的值(其中id属性非常重要,下一步将会使用id属性的值 引用该元素)。 (2)在其他资源文件中引用该UI控件;在源代码中定义一个该UI控件类型的变量 (成员变量、局部变量均可),使用findViewById()方法使该变量引用步骤(1)中添加的UI 控件。 1 00 移动应用开发技术 (3)定义处理UI控件某种事件的监听器,并调用步骤(2)中变量的相关方法,把监听 器与UI控件绑定,之后如果用户触发了该种UI事件,那么Android系统将会回调已经 绑定的监听器中的事件处理方法(例如,第4章中Button控件事件监听器的onClick()方 法,该方法由View.OnClickListener接口定义)。 上述步骤将会在后续各种控件的介绍中多次看到。 5.1.2 TextView 为展示Android系统中常见控件的使用方法,可在AndroidStudio中新建一个项目 UIWidgetDemo,使用自动创建的MainActivity以及布局文件activity_main.xml。 第2章已经使用TextView控件显示了HelloWorld! 的欢迎信息。 修改项目UIWidgetDemo中activity_main.xml的代码,具体如下所示。 图5.2 TextView 控件运行结果 观察上述布局文件中的标签,使用android:id属性给当前控件定义了 一个唯一的标识符,然后使用android:layout_width 和 android:layout_height属性指定了控件的宽度和高度。 Android中所有的控件都具有这两个属性,可选值有3种: match_parent、fill_parent和wrap_content,其中match_ parent和fill_parent的意义相同,现在更推荐使用match_ parent。match_parent表示让当前控件的大小和父布局的 大小一样,也就是由父布局决定当前控件的大小。wrap_ content表示让当前控件的大小能够刚好包含控件的内容, 也就是由控件的内容决定当前控件的大小。根据上述规 则,上述布局文件的代码表示让TextView 的宽度和父布 局的宽度(也就是手机屏幕的宽度)一样,而TextView 的 高度足够包含其中的内容就可以了。当然,除了上述选项 外,也可以对控件的宽度和高度指定固定的值,但是这样 做有时会在多种手机屏幕(大小和分辨率不同)的适配方 面出现问题。 下面通过android:text属性指定了TextView 中显示 的文本内容,运行该程序,运行结果如图5.2所示。 第5 章 UI 组件与布局1 01 虽然指定的文本内容正常显示了,但是好像并没有看出TextView 控件的宽度和手 机屏幕宽度相同,其实这是由于TextView 中的文本默认居左显示,虽然TextView 控件 的宽度充满了整个屏幕,但是由于文本内容不够长,因此从效果上看不出TextView 控件 的宽度。修改布局文件中TextView控件的对齐方式,代码如下所示。 使用android:gravity属性指定文字的对齐方式,可选值有top、bottom、left、right、 center等,也可以使用|同时指定多个值。这里指定的center,效果上等价于center_ vertical|center_horizontal,表示文字在垂直和水平方向都居中对齐。重新运行该程序, 运行结果如图5.3所示。 这也说明了TextView的宽度的确和屏幕宽度一样。 另外,还可以对TextView中文字的大小和颜色进行修改,代码如下所示。 通过android:textSize属性可以指定文字的大小,通过android:textColor属性可以 指定文字的颜色。在Android中,字体的大小使用sp(scaledpixels)作为单位。重新运行 程序,运行结果如图5.4所示。 除上述属性之外,TextView还有很多其他的属性,此处不再一一列举。 1 02 移动应用开发技术 图5.3 TextView 控件运行结果(居中对齐) 图5.4 TextView 控件运行结果(修改字体大小) 5.1.3 Button Button是应用程序中和用户进行交互的一种常用的控件。第4章中多次使用到 Button。从图5.1 可以看出,Button 类的直接父类是TextView 类,因此5.1.2 节中 TextView的属性Button都会自动继承得到。在布局文件activity_main.xml中添加一 个Button,代码如下: