Android编程权威指南(第二版)学习笔记(五)—— 第5章 第二个 Activity

本章主要讲述了如何新建一个 Acitivity ,并在两个 Activity 之间传递数据,最后挑战练习是如何在重建 Activity 时保留数据。

GitHub 地址:
第五章未完成挑战
第五章完成挑战问题1,2
第五章完成所有挑战问题

1. 新建一个 Activity

最好的方法是使用 Android Studio 自带的创建方法,若要手动创建,一定要有三个环环相扣的地方需要建立:

  • 一个 JAVA 类:即 Activity 类, 可以视需求继承 Activity 或者其他的衍生类
  • 一个布局文件:对于任意一个 Activity 来说,都需要加载一个布局文件,在 res/layout 文件夹下新建一个布局文件,并在代码中使用 setContentView() 方法加载布局
  • ★★★★★ 一定要在 AndroidManifest.xml 中声明新的 Activity!

2. 启动Activity

Activity 类中的一个函数 public void startActivity(Intent intent), 调用该方法时,启动 Activity 的请求直接发给了操作系统的 ActivityManager。ActivityManager 负责创建 Activity 实例并调用其 onCreate()方法。示意图如下:

基于 Intent 的交互

基于Intent的通信

Intent 对象是 component 用来与操作系统通信的一种媒介工具。Intent 类提供了多种构造方法以满足不同的使用需求, 这章使用的就是最简单的启动一个新的 Activity 的构造方法。

component 就是四大组件:Activity, Service, Broadcast Receiver, Content Provider

public Intent(Context packageContext, Class<?> cls)
//Class 对象必须已经在 AndroidManifest.xml 中声明才可以使用,否则将抛出 ActivityNotFoundException

3. Activity 间的数据传递

3.1 使用 Intent Extra

在使用 Intent 对象启动另一个 Activitiy 的时候使用了其构造方法,如果要让另一个 Activity 知道前一个 component 需要展示什么(比如用户到底点击了哪个按钮随之要展示什么详情),就需要在 Intent 中说明。使用 Intent 对象方法public Intent putExtra(String name, <Type> data) 将数据存到 Intent 对象内部,然后给操作系统。

这整个过程有点像送信:

  • 一个 component 应该先准备一个信封(Intent),在信封上写好发件人和收件人(显式 Intent 的构造方法)。
  • 接着写信(Intent Extra),装到信封里(Intent),用 startActivity() 方法把信投递给操作系统的 ActivityManager。
  • ActivityManager 看到收件人的地址,去找到收件人,敲他家的门(调用其 onCreate() 方法),然后把信给他。

这样,一个 Activity 就被启动了。

一般来说,我们会在一个 Activity 中写入自己的启动方法或者一个『用于获取启动本 Activity 的 Intent 对象』的方法,因为这样的话,其他 component 在启动时能够清楚地知道需要什么参数。比如可以写一个 public static void actionStart(Context, Extra)函数,传入参数是本 Activity 的上下文,和需要传递的额外信息,这样别的 component 在启动时,只需要调用该静态方法即可。

3.2 从子 Activity 获取返回结果

还是用送信来类比,如果一封信被另一个 Activity 收到了,他拆了信看完以后就丢弃了,并不会回信。那么如果发信者想要收信者回信,需要先跟 ActivityManager 说好,而且还要约定一个暗号,以便回信时不会弄错,然后 ActivityManager 再投递信,敲门并告诉另一个 Activity 应该回信。

也就是说,如果启动另一个 Activity 并希望其在退出时返回结果,那么应该使用下面的方法,即先跟 ActivityManager 说好,暗号就是 requestCode 。

public void startActivityForResult(Intent intent, int requestCode)

自己也要做好准备接受消息,即重写方法

protected void onActivityResult(int requestCode, int resultCode, Intent data)

这个多出来的 resultCode 顾名思义,就是结果的正确与否,一般会使用 Activity.RESULT_OK 或者 Activity.RESULT_CANCELED 来标志, 或者自定义常量 Activity.RESULT_FIRST_USER 以便根据 Activity 返回结果来做出不同操作。如果下一个 Activity 不设置结果的话(也就是不回信),用户退出该 Activity 时会默认返回 RESULT_CANCELED。

而回信的人只需要写信即可,直接使用 Activity 的方法:

public final void setResult(int requestCode, Intent data)
//或者
public final void setResult(int requestCode)

回传的数据也是使用 Intent 封装的。

3.3 最后大概总结一下这个过程

  • 如果需要在启动另一个 Activity 时传递数据,就使用 Intent 的 putExtra() 方法

  • 如果还需要返回结果,就要使用 startActivityForResult() 函数, 需要事先规定好 requestCode

  • 同时父 Activity 需要重写 onActivityResult() 函数,对返回的结果进行处理

  • 子 Activity 若要回传数据,调用 setResult() 方法将数据放入即可。

注: SharedPreferences 有时也能起到传递信息的作用,但是一般只用来保存基本类型的数据,所以作用有限,就像把东西放在一个共有的环境里,大家都知道那里有东西,谁需要都可以去取。

4. Activity 的使用与管理

对于一个应用来说,启动时系统只是先启动了其中的一个 Activity,这个 Activity 理应已经在 AndroidManifest.xml 文件中声明为 Launcher Activity。

对于所有应用,其 Activity 共享同一个『回退栈』。如果没有重写 onBackPressed() 函数的话,按下返回键就将当前 Activity 弹出栈顶,或者自己调用了 Activity.finish() 函数时也同样会弹出栈顶。

5. 章末挑战

  1. 用户作弊后,可以旋转 CheatActivity 来清除作弊痕迹。

这个问题比较好处理,问题原因是由于旋转时需使用新的布局文件,重新调用了 onCreate() 方法,从而导致作弊痕迹丢失。那么重写 onSaveInstanceState() 方法,将其保存,在 onCreate() 中对数据进行恢复即可。

  1. 作弊返回后, 用户可以旋转 QuizActivity 来清除 mIsCheater 变量值。

同上

  1. 用户可以不断单击NEXT按钮,跳到偷看过答案的问题,从而使作弊记录丢失。

由于每道题有每道题的作弊记录,所以我的思路是采用一个 boolean 数组记录作弊情况,并且这个数组也应该在旋转的时候进行保存,在应用启动期间长期存在即可。如果有长期保存的需求,就要用到 SharedPreferences 或者数据库了。


GitHub Page: kniost.github.io
简书:http://www.jianshu.com/u/723da691aa42

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,362评论 5 477
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,330评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,247评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,560评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,580评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,569评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,929评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,587评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,840评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,596评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,678评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,366评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,945评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,929评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,165评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 43,271评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,403评论 2 342

推荐阅读更多精彩内容