学习安卓开发[1] - 程序结构、Activity生命周期及页面通信

时间:2022-09-21 21:43:39

一、程序结构

Android原生应用采用了MVC的架构设计模式,因此可以将一个Android APP中的对象归为Model、View或Controller中的一种。

具体到某个实际的APP结构中,它一般会由若干个activity、layout文件和自定义类组成,activity是Android SDK中Activity类的实例,负责管理用户与应用界面的交互,应用的功能是通过编写Activity子类来实现的;layout文件则用于定义需要显示的UI对象以及指定它们在屏幕上所处的位置,layout文件的后缀为XML。

由此可知,layout文件等属于视图对象,此外Android还自带了很多可配置的视图类,在后面逐步了解。控制器则通常是Activity、Fragment或Service的子类。

学习安卓开发[1] - 程序结构、Activity生命周期及页面通信

二、layout文件内容

layout文件定义了界面显示的UI组件及其布局方式,对于下面这样一个简单界面

其layout文件内容为:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical">
<TextView
android:id="@+id/question_text_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="24dp" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal">
<Button
android:id="@+id/true_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/true_button" />
<Button
android:id="@+id/false_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/false_button" />
<Button
android:id="@+id/cheat_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/cheat_button"/>
<Button
android:id="@+id/next_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/next_button"
android:drawableRight="@drawable/arrow_right"/>
</LinearLayout>
</LinearLayout>

其组成有:

一个垂直的LinerLayout组件,包含一个TextView组件和一个水平的LinerLayout组件;

水平的LinerLayout组件中又包含4个Button组件。

先看一下这里面包含的一些后续会经常用到的属性:

1. android:layout_width和android:layout_height,可以设置为wrap_content(视图与其父视图大小相同)或match_content(视图会根据其内容自动调整大小)。可以看到作为根节点的LinerLayout也有layout_width和layout_height属性,这是因为Android系统为其提供了容纳整个应用的父视图。

2.android:orientation,orientation是LinerLayout组件具有的属性,它指定LinerLayout的子组件是水平放置还是水平放置。

3.android:text,TextView和Button具有text属性,指定组件要显示的文字内容。

三、字符串资源

可以看到android:text的值为类似"@string/next_button"这样的形式,这是对字符串资源的应用,字符串资源(string resource)在string.xml中定义。通过把字符串内容放置在字符串资源,然后再间接引用它们,这样可以方便地修改需要显示的内容,更重要的是便于应用的本地化。

比如@string/next_button在字符串资源中的形式为:

<string name="next_button">Next</string>

那么为什么在layout文件中输入“@string/”后,Android会自动提示出“next_button”呢,这要从资源ID说起。非代码形式的内容都属于资源,比如图像文件、音频文件、XML文件等,资源文件都存放在app/res的子目录下,string.xml的路径为app/res/values,layout.xml的路径为app/res/layout,要获取这些xml中定义的资源需要先知道对应的资源ID,所有资源的ID都存放在R.java文件中,将Android Studio的项目视图切换为Project后,可根据路径app/build/generated/source/r/debug/对于项目包名称/R.java找到R文件,在这里我们可以在public static final class string下找到

public static final int next_button=0x7f0b0025,这便是next_button的资源ID,资源ID都是int型。

R文件在编译时自动生成,手动修改可能会导致未知错误。修改资源内容后,R文件不会实时刷新,只有在应用安装到模拟器或物理设备时才会重新生成,Android Studio还另外保存有一份用于代码编译的隐藏的R文件。

四、Activity

1.组件的引用

一个页面的Activity与layout的名称有对应关系,比如activity_quiz.xml对应的activity名称为QuizActivity.java。在Activity中使用组件的第一步,也是通过资源ID获取该组件,比如引用一个Button时的代码为:

private Button mTrueButton;

...

mTrueButton=(Button) findViewById(R.id.true_button);

拿到组件后,就可以做后续的操作了,比如为Button设置监听器(listener):

mTrueButton.setOnClickListener(new View.OnClickListener(){

@Override

public void onClick(View v){

}

});

或者改变TextView的显示内容:

mQuestionTextView=(TextView) findViewById(R.id.question_text_view);

mQuestionTextView.setText(“New Text”);

2.Activity的生命周期

在使用Android Studio向导创建一个Activity后,默认会有onCreate方法:

@Override

protected void onCreate(Bundle savedinstanceState){

}

onCreate属于Activity的生命周期方法,此外还有onStart(), onResume(), onPause(), onStop(), onDestroy()。页面在不同的状态间切换时,这些方法会被Android系统执行

学习安卓开发[1] - 程序结构、Activity生命周期及页面通信

启动APP时,依次执行onCreate, onStart, onResume,直接进入运行态;

按Home键回到主页时,依次执行onPause, onStop,进入停止态;

点击返回键退出APP时,则会依次执行onPause, onStop和onDestroy,页面被销毁;

需要注意的是,旋转屏幕时也会依次执行onCreate, onStart, onResume,这是因为发生屏幕旋转时,Android会销毁当前activity,寻找合适的备选资源并重新创建。这一特性对于需要保存页面状态的activity会造成问题,因为重新创建activity会丢失当前页面的操作状态,这是我们不希望发生的。要解决这个问题,可以覆盖系统的onSaveInstanceState(Bundle)方法,在APP转入停止状态时,这个方法在onStop之前由系统调用,我们可以在这个方法中将activity视图状态相关的数据存入Bundle对象中:

@Override

public void onSaveInstanceState(Bundle savedInstanceState) {

super.onSaveInstanceState(savedInstanceState);

savedInstanceState.putInt(KEY_INDEX, mCurrentIndex);

}

然后在每次重新创建activity时尝试读取Bundle中的内容:

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

if (savedInstanceState != null) {

mCurrentIndex = savedInstanceState.getInt(KEY_INDEX);

}

....

}

五、页面通信

一般来说一个APP不可能只有一个页面,通过主页面打开子页面时就涉及到了页面间的通信。

Android使用基于Intent的通信方式,intent对象是component用来与操作系统通信的媒介工具。activity就是一种component对象。Intent是一种多用途通信工具,Intent类有多个构造方法,能满足不同的使用需要。

1.从父页面启动子页面

假设父页面为QuizActivity,子页面为CheatActivity,则从父页面启动子页面的方法为:

...

Intent intent = new Intent(QuizActivity.this, CheatActivity.class);

intent.putExtra(EXTRA_ANSWER_IS_TRUE, answerIsTrue);

startActivity(intent);

...

使用intent.putExtra方法可以在启动子页面的同时传入需要的值,然后子页面可读取传入值的方法为:

mAnswerIsTrue = getIntent().getBooleanExtra(EXTRA_ANSWER_IS_TRUE, false);

2.子页面返回结果给父页面

在很多场景中都需要子页面返回结果给父页面。有两个方法可以使用:

public final void setResult(int resultCode)

public final void setResult(int resultCode, Intent data)

resultCode的值为预定义常量,有:

Activity.RESULT_OK,对应确认操作

Activity.RESULT_CANCELED,对应取消操作

Activity.RESULT_FIRST_USER,用于自定义结果代码

使用public final void setResult(int resultCode, Intent data)即可将结果数据通过Intent返回给父页面。

相应的,在父页面要取得子页面的返回结果,需要覆盖onActivityResult(int, int, Intent方法)

    @Override

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

        if (resultCode != Activity.RESULT_OK) {

            return;

        }

        if (requestCode == REQUEST_CODE_CHEAT) {

            if (data == null) {

                return;

            }

            //TODO

        }

    }

学习安卓开发[1] - 程序结构、Activity生命周期及页面通信的更多相关文章

  1. 【Android实验】第一个Android程序与Activity生命周期

    目录 第一个Android程序和Activity生命周期 实验目的 实验要求 实验过程 1. 程序正常启动与关闭 2. 外来电话接入的情况 3. 外来短信接入的情况 4. 程序运行中切换到其他程序(比 ...

  2. Android学习路线(十二)Activity生命周期——启动一个Activity

    DEMO下载地址:http://download.csdn.net/detail/sweetvvck/7728735 不像其他的编程模式那样应用是通过main()函数启动的.Android系统通过调用 ...

  3. Android学习路线(十四)Activity生命周期——停止和重新启动&lpar;Stopping and Restarting&rpar;一个Activity

    正确地停止和重新启动你的activity在activity的生命周期中是一个非常重要的过程.这样可以确保你的用户感觉到你的应用一直都活着而且没有丢失进度.你的activity的停止和重新启动时有几个重 ...

  4. 学习安卓开发&lbrack;2&rsqb; - 在Activity中托管Fragment

    目录 在上一篇学习安卓开发[1]-程序结构.Activity生命周期及页面通信中,学习了Activity的一些基础应用,基于这些知识,可以构建一些简单的APP了,但这还远远不够,本节会学习如何使用Ac ...

  5. &period;Net程序员快速学习安卓开发-布局和点击事件的写法

    关注今日头条-做全栈攻城狮,学代码也要读书,爱全栈,更爱生活.提供程序员技术及生活指导干货. 本系列课程 致力于老手程序员可以快速入门学习安卓开发.系统全面的从一个.Net程序员的角度一步步学习总结安 ...

  6. 程序员带你学习安卓开发-XML文档的创建与解析

    这是程序员带你学习安卓开发系列教程.本文章致力于面向对象程序员可以快速学习开发安卓技术. 上篇文章:程序员带你学习安卓开发系列-Android文件存储 因知识连贯性推荐关注头条号:做全栈攻城狮.从头开 ...

  7. 程序员带你学习安卓开发系列-Android文件存储

    这是程序员带你学习安卓开发系列教程.本文章致力于面向对象程序员可以快速学习开发安卓技术. 上篇文章:.Net程序员快速学习安卓开发-布局和点击事件的写法 主要讲解了布局和点击事件的写法. 上篇文章补充 ...

  8. 程序员带你学习安卓开发,十天快速入-对比C&num;学习java语法

    关注今日头条-做全栈攻城狮,学代码也要读书,爱全栈,更爱生活.提供程序员技术及生活指导干货. 如果你真想学习,请评论学过的每篇文章,记录学习的痕迹. 请把所有教程文章中所提及的代码,最少敲写三遍,达到 ...

  9. Android学习整理之Activity生命周期篇

    一.Activity生命周期说明   Activity的四种状态: ⒈活动状态(Active or Running):也称为运行状态,处于Activity栈顶,在用户界面中最上层,完全能被用户看到,能 ...

随机推荐

  1. 再谈Newtonsoft&period;Json高级用法

    上一篇Newtonsoft.Json高级用法发布以后收到挺多回复的,本篇将分享几点挺有用的知识点和最近项目中用到的一个新点进行说明,做为对上篇文章的补充. 阅读目录 动态改变属性序列化名称 枚举值序列 ...

  2. ffmpeg&rsqb;ffmpeg使用参数的中文说明

    基本选项: -formats 输出所有可用格式 -f fmt 指定格式(音频或视频格式) -i filename 指定输入文件名,在linux下当然也能指定:0.0(屏幕录制)或摄像头 -y 覆盖已有 ...

  3. 3D旋转动画

    <!DOCTYPE html><html xmlns="http://www.w3.org/1999/xhtml"><head>    < ...

  4. corosync&plus;pacemaker实现高可用&lpar;HA&rpar;集群

    corosync+pacemaker实现高可用(HA)集群(一)     重要概念 在准备部署HA集群前,需要对其涉及的大量的概念有一个初步的了解,这样在实际部署配置时,才不至于不知所云 资源.服务与 ...

  5. Dapper 封装oracle底层访问数据库

    如下代码,修改成只支持oracle: using System; using System.Collections.Generic; using System.Data; using System.L ...

  6. 写一份简单的webpack2 的配置文件,无比简单

    这是一份自己用到的webpack2的配置写法,从看webpack2开始,发现自己越来越懒了,现在html文件都不想自己写了,直接自己生成... 哈哈,这次是可以无比完美的导入css啦 开发的时候在命令 ...

  7. JavaScript学习(三)

  8. &lbrack;LeetCode&rsqb; 255&period; Verify Preorder Sequence in Binary Search Tree&lowbar;Medium tag&colon; Preorder Traversal&comma; tree

    Given an array of numbers, verify whether it is the correct preorder traversal sequence of a binary ...

  9. Linux WiFi Deauthenticated Reason Codes

    Code Reason Explanation 0 Reserved Normal working operation 1 Unspecific Reason We don’t know what’s ...

  10. Codeforces 617B:Chocolate(思维)

    题目链接http://codeforces.com/problemset/problem/617/B 题意 有一个数组,数组中的元素均为0或1 .要求将这个数组分成一些区间,每个区间中的1的个数均为1 ...