请参考教材,全面理解和完成本章节内容... ...

本章将通过设计首个应用名为GeoQuiz, 介绍编写Android应用需掌握的一些基概念和设计方法。

移动系统的的应用也叫App,本章的App能测试用户的地理知识。图1-1显示了用户点击“对”按钮的结果。

emulator 降低版本 手机模拟低版本_emulator 降低版本

图1-1 正确答案应该是台湾,而不是海南岛

1.1  Android应用基础

GeoQuiz应用由一个activity(活动)和一个布局(layout)组成。

其中,Activity中文可以翻译为活动或者活动界面。

  • 从用户角度来看, Activity就是包含用户界面的一个大组件,主要用于和用户进行交互。一个应用程序中可以包含1个或多个Activity。
  • 从程序设计的角度来看,Activity是Android SDK中Activity类的一个具体实例,负责管理用户与信息屏的交互。Android应用程序的功能是通过编写一个个Activity子类来实现的。简单的应用可能只需一个子类,而复杂的应用则会有多个子类。

本章的GeoQuiz应用很简单,因此它只有一个Activity名为 QuizActivity (继承自 Activity 的子类)。QuizActivity 负责管理 图1-1所示的用户界面。

布局(layout)定义了一系列用户界面对象以及它们显示在屏幕上的位置。组成布局的定义保存在XML文件中。每个定义用来创建屏幕上的一个对象,如按钮或文本信息。

GeoQuiz应用包含一个名为activity_quiz.xml的布局文件,该文件中的XML标签定义了图1-1所示的用户界面。

通常,一个Activity对应一个layout(布局),如QuizActivity的布局是activity_quiz.xml文件。在本章中,QuizActivity管理着activity_quiz.xml文件定义的用户界面,它们之间的关系如图1-2所示。

 

emulator 降低版本 手机模拟低版本_用户界面_02

图1-2 Activity、布局文件和用户界面关系图

学习了这些基本概念后,我们来创建本书第一个应用。

1.2  创建 Android 项目

首先,在根目录下建一个目录,用来保存项目文件。英文命名,比如F:\Mywork\AS\ch1\,代表第一章的工程目录。

接下来,启动Android Studio 程序,选择右侧 Start a new Android Studio project菜单项;此时,Android Studio打开一个向导来帮助我们来创建一个新的项目。

在第一个向导窗口中,在应用名称(Application Name)处输入GeoQuiz,在公司域名(Company Domain)处输入jet.com(其中jet是我的英文名),如图1-3所示。此时包名处(Package Name)会自动更新为com.jet.geoquiz

在项目位置处(Project location)选择一个合适位置,不要有中文路径,如F:\Mywork\AS\ch1\,其中AS 代表Android 学习、ch1代表第一章。

emulator 降低版本 手机模拟低版本_用户界面_03

图1-3 创建新应用

注意,以上输入的包名遵循了“DNS反转”约定,亦即将个人或公司的域名反转后,在尾部附加上应用名称。遵循此约定可以保证包名的唯一性,这样,同一设备和Google Play商店的各类应用就可以区分开来。

  • Application Name此处填写想呈现给用户的应用名称,此处我们使用“GeoQuiz”。
  • Company domain 包名限定符,Android Studio会将这个限定符应用于每个新建的Android项目。
  • Package Name是应用的包命名空间(同Java的包的概念),我们也可以独立地编辑该包名。
  • Project location 存放项目的目录。

现在单击Next按钮。

接下来的四个选项用来配置应用如何与不同版本的Android设备适配。GeoQuiz应用只需使用默认设置,其他选项忽略。

Android开发工具每年会更新多次,因此当前的向导画面看起来可能会与图1-4略有不同。这一般不是问题,工具更新后,向导画面的配置选项应该不会有太大差别。

emulator 降低版本 手机模拟低版本_Android_04

图1-4 选择App运行的Android版本

现在单击Next按钮。

图1-5所示的窗口询问想要创建的activity类型。选择Blank Activity。

emulator 降低版本 手机模拟低版本_Android_05

图1-5 创建一个Blank activity

单击Next按钮继续

应用向导的最后一个窗口,命名activity子类为QuizActivity,如图1-6所示:

emulator 降低版本 手机模拟低版本_Android_06

图1-6 配置建的activity

最后,单击Finish按钮。Android Studio完成创建并打开新的项目。(有时还是漫长的等待…)

1.3  Android Studio 工作区导航

如图1-7所示(可放大),第一次运行 Android Studio时工作区窗口会打开多个视图,熟悉后,可以按需开关某些视图。

emulator 降低版本 手机模拟低版本_用户界面_07

图1-7 调整安排工作区窗口

整个工作区窗口分为不同的区域,这里统称为视图。最左边视图1是项目导航(Project)视图,通过它可以管理所有项目相关的文件。项目导航视图里的目录结构可以设置为“Android”或者“Project”类型,点击图1-7左上角红框可完成设置。我们采用“Android”结构显示项目文件目录;

中间部分视图2UI设计区代码编辑区视图。Android Studio默认在中间部分显示UI设计区 (打开 activity_quiz.xml文件)。

在工作区的底部视图3还有一些其他视图,显示一些编译信息、警告或建议信息、代码调试信息等。

工作区的每个视图都以分组面板(tab group)形式显示,可切换不同分组显示不同视图。

1.4  用户界面设计

通常,Android Studio向导会帮我们生成一个布局文件activity_quiz.xml。布局文件统一放置在\app\res\layout\目录, 所有layout文件都放在这里。

如图1-7所示,在中间部分已默认打开activity_quiz.xml布局文件,并在图形布局工具Design里显示了预览界面。虽然图形化布局工具非常好用,但为更好地理解布局的内部原理,我们还是先学习如何使用XML代码来定义布局。

在中间部分视图2的底部选择标为Text的标签页,从布局界面Design切换到XML代码界面Text

注意,activity_quiz.xml文件定义了默认的activity布局,但基本布局经常改变。一个典型的“Hello World”布局如代码清单1-1所示。你可以参照代码清单1-1的内容,修改“activity_quiz.xml”布局文件。其中粗体内容是需要你输入的,非粗体内容是之前代码。(注意,Android Stuido 1.4 Beta 3会生成content_quiz.xml文件,请其内容复制到activity_quiz.xml,注释掉 <include layout="@layout/content_quiz"/> )。

代码清单1-1 基本activity布局(activity_quiz.xml)

emulator 降低版本 手机模拟低版本_xml_08

应用activity的布局默认定义了两个组件(widget):RelativeLayoutTextView

组件是组成用户界面的构造模块。组件可以显示文字或图像、与用户交互,甚至是布置屏幕上的其他组件。按钮、文本输入控件和选择框等都是组件。

Android SDK内置了多种组件,通过配置各种组件可获得所需的用户界面及行为。每一个组件是View类或其子类(如TextViewButton)的一个具体实例。

图1-8展示了代码清单1-1中定义的RelativeLayoutTextView是如何在屏幕上显示的。

emulator 降低版本 手机模拟低版本_Android_09

图1-8 显示在屏幕上的默认组件

不过,图1-8所示的“Hello World”布局太简单,并不是我们需要的。

GeoQuiz应用的用户界面需要下列五个组件:

  • 一个垂直LinearLayout组件;
  • 一个TextView组件;
  • 一个水平LinearLayout组件;
  • 两个Button组件。

图1-9展示了以上组件是如何构成QuizActivity用户界面的。

emulator 降低版本 手机模拟低版本_xml_10

图1-9 布置并显示在屏幕上的组件

现在,我们重新定义在activity_quiz.xml文件中定义QuizActivity应用的用户界面:

由于修改内容多,请按照代码清单1-2所示,输入新代码。

代码清单1-2 在XML文件(activity_quiz.xml)中定义组件

emulator 降低版本 手机模拟低版本_xml_11

注:就算不能完全理解这些代码也没关系,你会在后续的学习中弄明白的。需要特别注意的是,开发工具无法完全校验布局XML内容,请避免输入或拼写错误。

根据所使用的工具版本不同,有三行以android:text开头的代码会产生错误信息(红色)。暂时忽略它们,稍后会处理。

将XML文件与图1-9所示的用户界面进行对照,可以看出组件与XML元素一一对应。元素的名称就是组件的类型。

各元素均有一组XML属性。属性可以看作是如何配置组件的指令。

为便于理解元素与属性的工作原理,接下来我们将以层次等级的视角来研究布局.

1.4.1 视图层级结构

组件之间有上下级关系(包含和被包含的关系),也有平级的关系。可以用图来描述这种关系,即视图层级结构图

请参考教材, 进一步理解本节内容...

1.4.2 组件属性

请参考教材,理解和完成本节内容... ...。

1.4.3 添加应用的字符串资源

每个项目都包含一个名为strings.xml的默认字符串文件。

在项目导航视图中,找到res\values目录,然后打开strings.xml文件。可以看到,项目模版已经默认添加了一些字符串资源。删除不需要的hello_world部分,添加GeoQuiz应用布局所需要的新的字符串,如代码清单1-3所示。

代码清单1-3 添加字符串资源(strings.xml)

 

emulator 降低版本 手机模拟低版本_xml_12

现在,在GeoQuiz项目的任何XML文件中,只要引用到@string/false_button,应用运行时,就会得到文本“”。

1.4.4 预览界面布局

在编辑区底部选择图形布局标签Design页进行界面布局预览,如图1-11所示。

emulator 降低版本 手机模拟低版本_用户界面_13

图1-11 在图形布局工具中预览界面布局(activity_quiz.xml)

1.5  从布局 XML 到视图对象

上一节,GeoQuiz应用的用户界面设计已经做好,但这仅仅是个静态的界面,用户还无法通过界面与我们的程序交互。如何处理这个问题?

想要实现交互,程序必须要知道用户在用户界面上做了那些动作,然后程序才能作出相应的反应(也叫响应用户事件),如何实现?

  • 第一,程序要知道用户界面上有哪些组件(界面元素),然后将它们分别绑定给对应的类对象。例如,将用户界面上按钮组件与一个Button类对象绑定,即将布局里的静态的“界面元素”变成动态的视图对象。
  • 第二,程序要时刻监听视图对象,如果用户与这些对象进行交互(如点击按钮),程序要做出反应。(在GeoQuiz应用中,程序要做出的反应就是“告诉用户的选择是否正确“)

本节先解决第一个问题:程序要知道用户界面上有哪些组件对象,即将布局里的“界面元素”内容转换为视图对象。

那么它是如何转换为视图对象的?答案就在 QuizActivity类中。

activity_quiz.xml 用来定义用户界面的布局文件,文件中每个 XML元素对应一个“界面元素”。我们可以利用QuizActivity类把每个“界面元素”赋给(绑定到)对应的视图对象.

在创建 GeoQuiz 项目的同时,也创建了一个名为 QuizActivity类,它是 AppCompatActivity子类。QuizActivity类文件存放在项目的\app\java\包目录下。

在项目导航视图中,依次展开\app\java\com.jet.geoquiz\, 打开QuizActivity.java文件。逐行查看其中的代码。

代码清单1-4 QuizActivity的默认类文件(QuizActivity.java)

emulator 降低版本 手机模拟低版本_xml_14

注意:教材中Activity 子类的父类都是Activity,为了更好的兼容,本文全部为AppCompatActivity ,如下所示:

原为:public class QuizActivity extends Activity{

改为:publicclassQuizActivityextendsAppCompatActivity{

QuizActivity类中,重写了(Override)onCreate(Bundle)方法。这样QuizActivity类的实例创建后,onCreate(Bundle)方法会被自动调用。

QuizActivity类的实例需要获取并管理属于自己的用户界面。可通过调用其父类的方法setContentView,获取布局文件资源,即用户界面,方法原型如下:

public void setContentView(int layoutResID)

通过传入布局资源的ID参数,该方法生成指定布局的视图并将其放置在屏幕上。布局视图生成后,布局文件包含的组件也随之以各自的属性定义完成实例化。

资源与资源ID

请参考教材…。

代码清单1-6 为按钮添加资源ID(activity_quiz.xml)

emulator 降低版本 手机模拟低版本_Android_15

1.6  组件的实际应用

请参考教材…

既然按钮有了资源ID,就可以在QuizActivity中直接获取它们。首先,在QuizActivity.java文件中增加两个成员变量。如代码清单1-8所示代码:

代码清单1-8 添加成员变量(QuizActivity.java)

emulator 降低版本 手机模拟低版本_Android_16

 

1.6.1 使用Alt+Enter快捷键

使用Alt+Enter快捷键,可以帮助我们快速更正错误;

当你在错误代码附近按下组合键Alt+Enter, Android Studio会依据代码自动帮你修正错误。包括,帮你决定应该导入哪些Java或Android SDK类包、修正简单语法错误。

对于上面的错误(Button 变红色)如果还没有解决,按下组合键Alt+Enter红色错误提示应该就会消失了。(如错误提示仍在,请检查代码是否拼写错误)

接下来,我们通过以下两个步骤,就能使用布局文件里的两个按钮:

  • 引用组件:引用生成的视图对象;
  • 设置监听器:为对象设置监听器,以响应用户操作。

1.6.2 引用组件

在activity中,可通过以下Activity提供的findViewById方法引用已生成的组件:

public View findViewById(int id)

该方法接受组件的资源ID作为参数,返回一个视图对象。

在QuizActivity.java文件中,使用按钮的资源ID获取生成的对象后,赋值给对应的成员变量,如代码清单1-9所示。注意,赋值前,必须先将返回的View转型(cast)为Button

代码清单1-9 引用组件(QuizActivity.java)

emulator 降低版本 手机模拟低版本_用户界面_17

文件保存后,如果有错误提示,检查一下activity_quiz.xml和strings.xml文件,看看里面是不是有错误. 修改错误后重新保存所有文件。

1.6.3 设置监听器

请参考教材,理解和完成本节内容... ...。

代码清单1-10 为True按钮设置监听器(QuizActivity.java)

emulator 降低版本 手机模拟低版本_用户界面_18

 

代码清单1-11 为False按钮设置监听器(QuizActivity.java)

emulator 降低版本 手机模拟低版本_用户界面_19

创建提示消息

接下来要实现的就是,分别单击两个按钮,弹出我们称为toast的提示消息。Android的toast指用来通知用户的简短弹出消息,但无需用户输入或做出任何操作。这里,我们要做的就是使用toast来告知用户其答案正确与否,如图1-12所示:

emulator 降低版本 手机模拟低版本_Android_20

图1-12 toast反馈消息提示

首先回到strings.xml文件,如代码清单1-12所示,为toast添加消息显示用的字符串资源。

代码清单1-12 增加toast字符串(strings.xml)

emulator 降低版本 手机模拟低版本_用户界面_21

通过调用来自Toast类的以下方法,可创建一个toast:

public static Toast makeText(Context context, int resId, int duration)

该方法的Context参数通常是Activity的一个实例(Activity本身就是Context的子类)。第二个参数是toast待显示字符串消息的资源ID。Toast类必须利用context才能找到并使用字符串的资源ID。第三个参数通常是两个Toast常量中的一个,用来指定toast消息显示的持续时间。

创建Toast后,可通过调用Toast.show()方法使toast消息显示在屏幕上。

QuizActivity代码里,分别对两个按钮的监听器调用makeText()方法,如代码清单1-13所示。在添加makeText()时,可利用Android Studio的代码自动补全功能,让代码输入工作更加轻松。

代码清单1-13 创建提示消息(QuizActivity.java)

emulator 降低版本 手机模拟低版本_emulator 降低版本_22

1.7  使用模拟器运行应用

要运行Android应用,需使用硬件设备或者虚拟设备(virtual device)。包含在开发工具中的Android设备模拟器可提供多种虚拟设备。(也可以使用海马玩模拟器 Droid4X等虚拟机)

要想创建Android虚拟设备(AVD),在Android Studio中,选择Tools->Android->AVD Manager菜单项,当AVD管理器窗口弹出时,点击窗口左下的Create Virtual Device按钮。

在随后弹出的对话框中,可以看到有很多配置虚拟设备的选项。按照 一系列图1-13所示进行配置。

emulator 降低版本 手机模拟低版本_xml_23

图1-13-1 创建新的AVD

接下来,选择要模拟的手机(尽量选择低版本手机,速度快),建议选择Nexus S如下图:

emulator 降低版本 手机模拟低版本_用户界面_24

图1-13-2 选择要模拟的手机(Select Hardware)

接下来,选择一个系统镜像(Android版本和虚拟机CPU),Level17 ,x86如下图:

emulator 降低版本 手机模拟低版本_xml_25

图1-13-3 选择要模拟的手机(Select Hardware)

最后,给新建的AVD命名、设置显示比例等,默认就好如下图:

emulator 降低版本 手机模拟低版本_xml_26

图1-13-4 AVD命名、设置显示比例等

AVD创建成功后,我们用它运行GeoQuiz应用:

  • 首先,选择Tools->Android->AVD Manager菜单项,运行之前新建的虚拟机(有点慢)
  • 然后,在菜单Run->Edit Configurations 里选择GeoQuiz
  • 最后,选择Run->Run ‘GeoQuiz’, 运行GeoQuiz应用。

Android会列表让你选择当前的虚拟机或实体机设备如图1-14,然后安装应用包(APK)并运行应用。

emulator 降低版本 手机模拟低版本_用户界面_27

图1-14 AVD命名、设置显示比例等

启动虚拟机可能比较耗时,请耐心等待。设备启动完成,应用运行后,就可以在应用界面点击按钮,让toast告诉我们答案。(注意,如果应用启动运行后,我们凑巧不在电脑旁,回来时,就可能需要解锁AVD。如同一台真实设备,AVD闲置一定时间会自动锁上。)

如何你没有实体机,建议保持模拟器一直运行,这样就不必在反复运行调试应用时,痛苦地等待AVD启动了。单击回退按钮(即AVD模拟器上的U型箭头按钮)可以停止应用。需要调试变更时,再通过Android Studio重新运行应用。

虽然模拟器非常有用,但在真实设备上测试应用能够获得更准确的结果。在第2章中,我们将在真实硬件设备上运行GeoQuiz应用,并且为GeoQuiz应用添加更多地理知识问题,以供用户回答。