Android《第一行代码》——第二章 活动

活动的基本用法

创建活动

首先创建一个空项目,右击com.example.activitytest包→New→Activity→Empty Activity,弹出一个创建活动的对话框。将活动命名,并且不要勾选Generate Layout File和Launcher Activity
在这里插入图片描述
在这里插入图片描述
创建任何活动都应该重写onCreate()方法,Android Studio已经自动重写好。

创建和加载布局

右击app/src/main/res目录→New→Directory会弹出一个目录窗口,创建一个layout目录,然后对着layout右键→Newyou→Layout resource file会弹出新建布局资源文件的窗口,我们命名为first_layout,根元素默认LinearLayout,这时就会看到布局编辑器。
在这里插入图片描述
我们在这里添加一个按钮

	<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
    <Button
        android:id="@+id/button_1"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="Button 1"/>
</LinearLayout>

预览结果如下
在这里插入图片描述
这里添加了一个Button元素,并且添加了几个元素,android:id是给当前的元素定义一个唯一的标识符,之后可以在代码中对该元素操作。XML定义使用@id/id_name的语法。
接下来就要在在活动中加载这个布局,回到FirstActivity,在OnCreate()中加入代码

	public class FirstActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.first_layout);
        }
      }

在AndroidMainfest文件中注册

活动声明要放在<application>标签内,这里是通过<activity>标签来对活动进行注册的,在<activity>标签内我们使用了android:name

	<application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/Theme.Activitytest">
        <activity android:name=".FirstActivity"></activity>
    </application>

<activity>内部添加<intent-filter>标签,除此之外,我们还可以使用android:label指定活动中标题栏的内容

	<activity
            android:name=".FirstActivity"
            android:label="This is FirstActivity">
	<intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>

在这里插入图片描述
标题栏下面就是在布局文件first_layout.xml中编写界面

活动中使用Toast

Toast是系统提供的一种提醒方式,这些信息提醒一段时间后就会消失。
首先要定义一个弹出Toast的触发点,利用之前建立好的按钮来创立。
onCreate()中添加如下代码

	    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.first_layout);
        Button button1 = (Button) findViewById(R.id.button_1);
            button1.setOnClickListener(new View.OnClickListener(){
                @Override
                public void onClick(View v){
                    Toast.makeText(FirstActivity.this,"You clicked Button 1",
                            Toast.LENGTH_SHORT).show();
                }
            });
        }

在活动中,通过findViewById()方法获取到在布局文件中定义的元素,这里我们传入R.id.button_1,来获得按钮实例,这个值是刚才在first_ layout.xml 中通过android:id属性指定的。findViewById()方法返回的是一个View对象,我们需要向下转型将它转成Button对象。得到按钮的实例之后,我们通过调用setOnClickListener()方法为按钮注册一个 监听器,点击按钮时就会执行监听器中的onClick()方法。因此,弹出Toast的功能当然是要在onClick()方法中编写了。

Toast的用法非常简单,通过静态方法makeText()创建出一个Toast对象,然后调用show()将Toast显示出来就可以了。这里需要注意的是,makeText()方法需要传入3个参数。第一个参数是Context,也就是Toast要求的上下文,由于活动本身就是一个Context对象,因此这里直接传人FirstActivity. this即可。第二个参数是Toast显示的文本内容,第三个参数是Toast 显示的时长,有两个内置常量可以选择Toast. LENGTH SHORTToast. LENGTH LONG
请添加图片描述

在活动中使用Menu

首先在res目录下新建一个menu文件夹,右击res目录→New→Directory, 输人文件夹名menu, 点击OK。接着在这个文件夹下再新建一个名叫main的菜单文件,右击menu 文件夹→New →Menu resource file
然后再main.xml中添加如下代码

	<menu xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:id="@+id/add_item"
        android:title="Add"/>
    <item
        android:id="@+id/remove_item"
        android:title="Remove"/>
</menu>

这里我们创建了两个菜单项,其中<item>标签就是用来创建具体的某一个菜单项,然后通过android:id给这个菜单项指定一个唯一的标识符,通过android:title给这个菜单项指定一个名称。
重写onCreateOptionMenu()方法

	@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.main,menu);
        return true;
    }

通过getMenuInflater()方法能够得到MenuInflater对象,再调用它的inflate()方法就可以给当前活动创建菜单了。inflate()方法接收两个参数,第一个参数用于指定我们通过哪一个资源文件来创建菜单,这里当然传入R. menu . main。第二个参数用于指定我们的菜单项将添加到哪一个Menu对象当中,这里直接使用onCreateOptionsMenu( )方法中传人的menu参数。然后给这个方法返回true,表示允许创建的菜单显示出来,如果返回了false, 创建的菜单将无法显示。
再定义菜单响应事件

 @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case R.id.add_item:
                Toast.makeText(this, "You clicked Add", Toast.LENGTH_SHORT).show();
                break;
            case R.id.remove_item:
                Toast.makeText(this, "you clicked Remove", Toast.LENGTH_SHORT).show();
                break;
            default:
        }
        return true;
        }

onOptionsItemSelected()方法中,通过调用item. getItemId( )来判断我们点击的是哪一个菜单项,然后给每个菜单项加人自己的逻辑处理,这里我们就活学活用,弹出一个刚刚学会的Toast
请添加图片描述

请添加图片描述

使用Intent在活动间穿梭

Intent可以实现在两个不同活动之间跳转

显式Intent

1.获得Intent实例,例:Intent intent=new Intent(Context,Class(指定想要启动的目标活动))。

2.调用startActivity(Intent)方法启动目标活动。

 button1.setOnClickListener(new View.OnClickListener() {
 public void onClick(View v){//显式Intent
             Intent intent = new Intent(FirstActivity.this,SecondActivity.class);
             startActivity(intent);
               }

这里的Context上下文可以理解为启动活动的一个环境。
请添加图片描述
SecondActivity界面

隐式Intent

用活动的配置信息来判断要启哪一个活动

1.给要启动的活动配置actioncategory信息。

 <activity android:name=".SecondActivity">
            <intent-filter>
                <action android:name="com.example.activitytest.ACTION_START" />
                <category android:name="android.intent.category.DEFAULT" />
                <category android:name="com.example.activitytest.MY_CATEGORY" />
            </intent-filter>
        </activity>

2.获得Intent实例
3.调用intent.addCategory(String(category信息))方法给Intent配置category信息。
4.调用startActivity(Intent)方法启动活动。

	 button1.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v){//隐式Intent
                    Intent intent = new Intent("com.example.activitytest.ACTION_START");
                    intent.addCategory("com.example.activitytest.MY_CATEGORY");
                    startActivity(intent);
                }
           });

注意:只有action于category信息同时匹配才会启动相应活动,每个活动只能配置一个action信息,但可以配置多个category信息。

向下活动传递数据

在启动活动的时候可以传递数据
1.调用putExtra()方法
2.书写要传入的数据

button1.setOnClickListener(new View.OnClickListener() {
                @Override
		public void onClick(View v){//向下传递字符串
               String data ="Hello SecondActivity";
                Intent intent = new Intent(FirstActivity.this,SecondActivity.class);
                intent.putExtra("extra_data",data);
                startActivity(intent);
                }
          });

3.在下一个活动中实例化Intent并调用getStringExtra()方法,传入键值,即可得到数据

	protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.second_layout);
        Intent intent = getIntent();
        String data = intent.getStringExtra("extra_data");
        Log.d("SecondActivity",data);
        }

打开logcat查看信息
在这里插入图片描述

返回数据给上一个活动

1.调用startActivityForResult()方法,用于启动活动的,但这个方法期望在活动销毁的时候能够返回一个结果给上一个活动。

button1.setOnClickListener(new View.OnClickListener() {
                @Override
	                public void onClick(View v) {//向上传递数据
                    Intent intent = new Intent(FirstActivity.this, SecondActivity.class);
                    startActivityForResult(intent, 1);
                }
                           });

2.在下一个活动注册一个事件去实现该效果
3.调用setResult()专门用于向上一个活动返回数据的

	 @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.second_layout);
        Button button2 = (Button)findViewById(R.id.button_2);
        Intent intent = getIntent();
        String data = intent.getStringExtra("extra_data");
        Log.d("SecondActivity",data);
        button2.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent();
                intent.putExtra("data_return", "Hello FirstActivity");
                setResult(RESULT_OK,intent);
                finish();
            }
        });
    }

4.在第一个活动中,重写onActivityResult()方法,通过检查requestCode的值来判断数据来源,再通过resultCode的值来判断处理结果是否成功,最后从打data中打印出来。

	 @Override
    protected void onActivityResult(int requestCode,int resultCode,Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        switch (requestCode) {
            case 1:
                if (resultCode == RESULT_OK) {
                    String returnedData = data.getStringExtra("data_return");
                    Log.d("FirstActivity", returnedData);
                }
                break;
            default:
        }
    }

活动的生命周期

返回栈

Android是使用任务( Task)来管理活动的,一个任务就是一-组存放在栈里的活动的集
合,这个栈也被称作返回栈( Back Stack )。栈是一种后进先出的数据结构,在默认情况下,每当
我们启动了一个新的活动,它会在返回栈中人栈,并处于栈顶的位置。而每当我按下Back键
或调用finish()方法去销毁一个活动时,处于栈顶的活动会出栈,这时前一个入栈的活动就会
重新处于栈顶的位置。系统总是会显示处于栈顶的活动给用户。
在这里插入图片描述

活动状态

每个活动在其生命周期中最多可能会有4个状态。

  • 1.运行状态
    当一个活动位于返回栈的栈顶时,这是活动就处于运行状态。
  • 2.暂停状态
    当一个活动不再处于栈顶位置,但仍然可见时,这时活动就会处于暂停状态。
  • 3.停止状态
    当一个活动不再处于栈顶位置,且完全不可见时,就进入了停止状态。
  • 4.销毁状态
    当一个活动自从返回栈中移除后就变成了销毁状态。

活动的生存期

  • onCreate()
    第一次创建时候调用,在这个方法中完成活动的初始化操作,比如加载布局、绑定事件。
  • onStart()
    该方法在活动由不可见变为可见时调用。
  • onResume()
    该方法在活动准备与用户进行交互时调用,此时活动一定处于栈顶且处于运行状态。
  • onPause()该方法在系统准备去启动或恢复另一个活动时调用。该方法的执行速度一定要快,否则会影响到新栈顶活动的使用。
  • onStop()该方法在活动完全不可见时调用,与onPause()方法的区别在于,若启动的新活动是一个对话框活动,那么onPause()方法会得到执行,而onStop()方法并不会执行。
  • onDestroy()该方法会在活动销毁前执行,之后活动的状态就会变为销毁状态。
  • onRestart()该方法会在活动由停止状态变为运行状态之前调用,也会就是活动被重新启动了。
    请添加图片描述

活动被回收了怎么办

如果一个活动进入了停止状态,那么该活动是有可能被系统回收的,因此可能会导致数据丢失。
1.重写onSaveInstanceState()方法,该方法可以保证在活动被回收之前获得调用,可以在其中调用putString(键,值)方法来保存数据。

 protected void onSaveInstanceState(@NonNull Bundle outState) {
        super.onSaveInstanceState(outState);
        outState.putString("data_key",tempData);//根据类型调用不同的方法
 }

2.在活动的onCreate()方法中调用getString(键)方法取出数据进行恢复。

  if(savedInstanceState!=null){
            String name=savedInstanceState.getString("name");
  }

活动的启动模式

活动共有4种启动模式,分别是standard,singleTop,singleTask,singleInstance,可以在AndroidManifest.xml中通过给< activity >标签指定android:launchMode属性来选择启动模式。

  • standard:
    默认模式,每当启动一个新的活动,就会在返回栈中入栈,并处于栈顶位置。该模式下无论这个活动是否在返回栈中存在,每次启动都会创建该活动的新实例。
    在这里插入图片描述

  • singleTop:
    该模式下,每当启动一个新的活动,如果发现返回栈的栈顶已是该活动,则可以直接使用它而不会再创建新的实例。
    在这里插入图片描述

  • singleTask:
    该模式下,每当启动一个新的活动,系统首先会在返回栈中检查是否存在该活动的实例,若存在就直接使用,并让该活动之上的所有活动出栈,若不存在则创建新的实例。
    在这里插入图片描述

  • singleInstance
    该模式下的活动会启用一个新的返回栈来管理这个活动。这个模式解决了其它程序和我们的程序共享一个活动实例的问题。
    在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值