【Android UI设计与开发】第12期:顶部标题栏(三)ActionBar实现层级导航的返回效果

转载请注明出处: http://blog.csdn.net/yangyu20121224/article/details/9059459      

今天我们继续来讲解ActionBar的使用,不清楚这个类的读者可以翻阅博主前几篇的文章或者在网络上查阅相关

的资料,关于这个类讲解的文章还是很多的,功能确实也很强大。好的,话不多说,让我们赶快进入正题吧。

一、使用应用图标实现层级导航

在默认的情况下,应用程序图标显示在操作栏的左边。你能够把这个图标当做操作项来使用,应用程序可以在这

个图标上响应以下两个操作其中之一:

<1> 返回应用程序的“主”Activity;

<2> 向应用程序上级页面导航。

要实现应用程序图标能够向上导航,首先就要在你的ActionBar中调用SetDisplayHomeAsUpEnabledtrue(true)方法。

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    setContentView(R.layout.main);
    ActionBar actionBar = getActionBar();
    actionBar.setDisplayHomeAsUpEnabled(true);
    ...
}

当用户触摸这个图标时,系统会调用Activity带有android.R.id.home ID的onOptionsItemSelected()方法。在这个响

应中,你既可以启动主Activity,也可以返回你的应用程序结构化层次中用户上一步操作的界面。

如果你要通过应用程序图标的响应来返回主Activity,那么就应该在Itent对象中包括

FLAG_ACTIVITY_CLEAR_TOP标识。用这个标记,如果你要启动的Activity在当前任务中已经存在,那么,堆栈中这

个Activity之上的所有的Activity都有被销毁,并且把这个Activity显示给用户。添加这个标识往往是重要的,因为返回主

Activity相当与一个回退的动作,因此通常不应该再创建一个新的主Activity的实例,否则,最终可能会在当前任务中产

生一个很长的拥有多个主Activity的堆栈。

例如,下例的onOptionsItemSelected()方法实现了返回应用程序的主Activity的操作:

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {
        case android.R.id.home:
            Intent intent = new Intent(this, HomeActivity.class);
            intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
            startActivity(intent);
            return true;
        default:
            return super.onOptionsItemSelected(item);
    }
}

在用户从另一个应用程序进入当前Activity的情况下,你可能还想要添加FLAG_ACTIVITY_NEW_TASK标识。这

个标识确保在用户返回主页或上级页面时,新的Activity不会被添加到当前的任务中,而是在属于你自己的应用程序的

任务中启动。例如,如果用户通过被另一个应用程序调用的Intent对象启动了你的应用程序中的一个Activity,那么选

择操作栏图标来返回主页或上级页面时,FLAG_ACTIVITY_CLEAR_TOP标识会在属于你的应用程序的任务中启动这

个Activity(不是当前任务)。系统既可以用这个新的Activity做根Activity来启动一个新的任务,也可以把存在后台的拥

有这个Activity实例的一个既存任务带到前台来,并且目标Activity会接受onNewIntent()回调。因此,如果你的Activity

要接收另一个应用程序的Intent对象,那么通常应该给这个Intent对象添加FLAG_ACTIVITY_NEW_TASK标识,如:

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {
        case android.R.id.home:
            // This is called when the Home (Up) button is pressed
            // in the Action Bar.
            Intent parentActivityIntent = new Intent(this, MyParentActivity.class);
            parentActivityIntent.addFlags(
                    Intent.FLAG_ACTIVITY_CLEAR_TOP |
                    Intent.FLAG_ACTIVITY_NEW_TASK);
            startActivity(parentActivityIntent);
            finish();
            return true;
    }
    return super.onOptionsItemSelected(item);
}

当当前的activity从属于一个不同应用的任务调出时,按下图标按钮应该创建该应用的一个新任务。

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {
        case android.R.id.home:
            Intent upIntent = new Intent(this, MyParentActivity.class);
            if (NavUtils.shouldUpRecreateTask(this, upIntent)) {
                // This activity is not part of the application‘s task, so create a new task
                // with a synthesized back stack.
                TaskStackBuilder.from(this)
                        .addNextIntent(new Intent(this, MyGreatGrandParentActivity.class))
                        .addNextIntent(new Intent(this, MyGrandParentActivity.class))
                        .addNextIntent(upIntent)
                        .startActivities();
                finish();
            } else {
                // This activity is part of the application‘s task, so simply
                // navigate up to the hierarchical parent activity.
                NavUtils.navigateUpTo(this, upIntent);
            }
            return true;
    }
    return super.onOptionsItemSelected(item);
}

二、在Fragments中实现层级导航

当在应用中使用fragments时,单一的FragmentTransaction对象能够表示环境的变化,应该被添加到back堆栈。

例如,如果你要实现一个master/detail流程,通过换出fragments,你应该确保在detail界面上点击Back按钮回退到

master界面。

 getFragmentManager().beginTransaction().add(detailFragment, "detail")
          // Add this transaction to the back stack and commit.
        .addToBackStack()
        .commit();

如果FragmentTransaction对象在back堆栈上,activity的FragmentManager会处理Back按钮的点击事件。当这一

事件发生时,FragmentManager从back堆栈中弹出最近一次事务,并进行反向的行为。如果你的应用程序更新其他用

户界面元素来反应当前fragment的状态,例如action bar,记得在commit事务的时候更新UI。

getFragmentManager().addOnBackStackChangedListener(
        new FragmentManager.OnBackStackChangedListener() {
            public void onBackStackChanged() {
                // Update your UI here.
            }
        });

三、导航到外部界面

当启动另一个应用程序的activity来允许用户,写一个邮件,或挑选一个照片附件,你一般不会想让用户在Launcher中重新启动程序时回到这个界面。这会对用户造成混淆。为了阻止这种事情的发生,简单的对intent添加FLAG_ACTIVITY_CLEAR_WITH_TASK_RESET标签来启动外部的activity:

Intent externalActivityIntent = new Intent(Intent.ACTION_PICK);
externalActivityIntent.setType("image/*");
externalActivityIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET);
startActivity(externalActivityIntent);

四、实现的效果图

 

五、项目结构图

六、详细代码编写

1、这个项目的代码不多,首先是主布局页面,activity_main.xml:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:id="@+id/other_btn"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_marginTop="160dp"
        android:text="Other_Activity" />

    <Button
        android:id="@+id/external_btn"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:layout_below="@+id/other_btn"
        android:text="External_Activity" />

</RelativeLayout>

2、然后是另一个界面的布局,activity_other.xml:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

</RelativeLayout>

3、主界面Activity类,MainActivity.java:

package com.yangyu.myactionbar04;

import android.app.ActionBar;
import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.View;

public class MainActivity extends Activity {

    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initView();
    }

    /**
     * 初始化组件
     */
    private void initView(){
        final ActionBar actionBar = getActionBar();

        actionBar.setHomeButtonEnabled(false);    

        this.findViewById(R.id.other_btn).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Intent intent = new Intent(MainActivity.this, OtherActivity.class);
                startActivity(intent);
            }
        });

        this.findViewById(R.id.external_btn).setOnClickListener(new View.OnClickListener() {
             @Override
             public void onClick(View view) {
                 //调用图片浏览器
                 Intent externalActivityIntent = new Intent(Intent.ACTION_PICK);
                 externalActivityIntent.setType("image/*");
                 externalActivityIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET);
                 startActivity(externalActivityIntent);
             }
         });
    }
}

4、进入到另一个Activity界面,OtherActivity.java:

package com.yangyu.myactionbar04;

import android.app.ActionBar;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.support.v4.app.NavUtils;
import android.support.v4.app.TaskStackBuilder;
import android.view.MenuItem;

public class OtherActivity extends FragmentActivity {

    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_other);

        final ActionBar actionBar = getActionBar();

        actionBar.setDisplayHomeAsUpEnabled(true);
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case android.R.id.home:
                Intent upIntent = new Intent(this, MainActivity.class);
                if (NavUtils.shouldUpRecreateTask(this, upIntent)) {
                    TaskStackBuilder.from(this)
                            //如果这里有很多原始的Activity,它们应该被添加在这里
                            .addNextIntent(upIntent)
                            .startActivities();
                    finish();
                } else {
                    NavUtils.navigateUpTo(this, upIntent);
                }
                return true;
        }
        return super.onOptionsItemSelected(item);
    } 

}

源码下载地址

时间: 2024-10-09 00:46:09

【Android UI设计与开发】第12期:顶部标题栏(三)ActionBar实现层级导航的返回效果的相关文章

【Android UI设计与开发】3.引导界面(三)实现应用程序只启动一次引导界面

大部分的引导界面基本上都是千篇一律的,只要熟练掌握了一个,基本上也就没什么好说的了,要想实现应用程序只启动一次引导界面这样的效果,只要使用SharedPreferences类,就会让程序变的非常简单,下面来详细介绍一下这个类的使用方法 1.SharedPreferences的详细介绍和用法 其实在 20.游戏开发基础(游戏数据存储)中已经有过介绍了,为了文章的完整还是再介绍一遍. 做软件开发应该都知道,很多软件会有配置文件,里面存放这程序运行当中的各个属性值,由于其配置信息并不多,如果采用数据库

【Android UI设计与开发】6.底部菜单栏(三)使用Fragment+PopupWindow仿QQ空间最新版底部菜单栏

直接看栗子吧,效果基本实现,界面微调和弹窗的优化,去做的话会很耗时说,暂时就酱紫了.上传效果动态图太大了,直接手机截图的效果图如下: 至于代码的实现主要就是自定义的菜单栏,和用 PopupWindow 实现弹窗了.仔细看代码很好懂的. 1.主界面布局代码如下: <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.and

【Android UI设计与开发】第05期:引导界面(五)实现应用程序只启动一次引导界面

[Android UI设计与开发]第05期:引导界面(五)实现应用程序只启动一次引导界面 jingqing 发表于 2013-7-11 14:42:02 浏览(229501) 这篇文章算是对整个引导界面开发专题的一个终结了吧,个人觉得大部分的引导界面基本上都是千篇一律的,只要熟练掌握了一个,基本上也就没什么好说的了,要是在今后的开发中遇到了更好玩,更有趣的引导界面,博主也会在这里及时的跟大家分享,今天的内容主要是教大家的应用程序只有在第一次启动的时候显示引导界面,以后在启动程序的时候就不再显示了

【转】【Android UI设计与开发】第07期:底部菜单栏(二)Fragment的详细介绍和使用方法

原始地址:http://blog.csdn.net/yangyu20121224/article/category/1431917/1 由于TabActivity在Android4.0以后已经被完全弃用,那么我就不再浪费口水继续讲解它了,取而代之的是Fragment.Fragment是Android3.0新增的概念,Fragment翻译成中文是碎片的意思,不过却和Activity十分的相似,这一篇我花大量的篇幅来详细的讲解Fragment的介绍和使用方法. 一.Fragment的基础知识介绍  

【Android UI设计与开发】第09期:底部菜单栏(四)Fragment+PopupWindow仿QQ空间最新版底部菜单栏

转载请注明出处:http://blog.csdn.net/yangyu20121224/article/details/9023451          在今天的这篇文章当中,我依然会以实战加理论结合的方式教大家如何设计出自己觉得很炫的UI界面.好的,话不多说,进入正题.今天的这篇文章主要是以仿QQ空间的底部菜单栏效果为主,实现的效果有: <1>实现了点击按钮时的切换图片效果: <2>实现了点击按钮时的切换界面效果: <3>实现了点击中间圆形按钮时弹出菜单以及按钮图片切

【Android UI设计与开发】第10期:顶部标题栏(一)ActionBar详细概述和简单示例

转载请注明出处:http://blog.csdn.net/yangyu20121224/article/details/9042387   由于是刚开始写博客,所以一开始在格式上也没有太在意,今天偶然间翻阅自己的博客,却发现字体.代码以及图片什么的都几乎快挤到了一起,自己都觉得看着很难受,更别说别的读者了.为了大家能够读的清楚.看的明白,今天博主稍微花了一点时间把这个专题前几期文章的标题和格式全都改了一遍.希望读者们继续支持,你们的支持也是我最大的动力! 一.ActionBar介绍 在Andro

【Android UI设计与开发】第13期:顶部标题栏(四)自定义ActionBar风格和样式

转载请注明出处:http://blog.csdn.net/yangyu20121224/article/details/9087941   这篇文章将对ActionBar专题前面几篇学习过的内容做一个总结,顺便运用以前学过的知识实现一个自定义样式的ActionBar标题栏效果.话不多说,进入今天的正题. 一.实现效果图 竖屏效果图:最左边是Logo图标,右边是工具栏按钮,点击Menu键显示其余的按钮键,下方是Tab标签选项. 横屏效果图:竖屏中的Tab选项标签变成了中间的下拉导航按钮 二.项目结

【Android UI设计与开发】第14期:顶部标题栏(五)两种方式实现仿微信标题栏弹窗效果

转载请注明出处:http://blog.csdn.net/yangyu20121224/article/details/9093821         博主在这篇文章中将会继续围绕顶部标题栏专题来进行实例讲解,今天要讲解的主题是分别使用PopupWindow和Activity两种不同的方式来实现仿微信顶部标题栏弹窗的这样一个效果. 一.实现效果图 这里为了演示方便,我将两种方法放在一个应用程序中演示,这个是主界面 虽然两种实现的方式不一样,但是最终的效果图都是差不多的     二.项目结构图  

【Android UI设计与开发】8.顶部标题栏(一)ActionBar 奥义&#183;详解

原文地址:http://www.cnblogs.com/yc-755909659/p/4290784.html 一.ActionBar介绍 在Android 3.0中除了我们重点讲解的Fragment外,Action Bar也是一个非常重要的交互元素,Action Bar取代了传统的tittle bar和menu,在程序运行中一直置于顶部,对于Android平板设备来说屏幕更大它的标题使用Action Bar来设计可以展示更多丰富的内容,方便操控. 二.ActionBar的功能 用图的方式来讲解