知识背景

Fragment在当前的Android开发中,有两种引用方式,一个是 Android 3.0 时加入的,一个是supportV4包中的。这里简称为Fragment3.0FragmentV4

Fragment中的返回

在Fragment中经常用到自定义标题栏,而返回按钮的点击事件一般设置为:getActivity().onBackPressed();,这样可以使得点击返回按钮和点击手机上的返回键的效果一致,即调用所在Activity的onBackPressed();

那么可能会造成一个问题:

本来你是想点击返回按钮让当前的Fragment出栈,显示上一个Fragment,但是却关闭了整个Fragment所在的Activity

即 启动Activity–>显示FragmentA–>显示FragmentB–>用户点击返回按钮或者手机上的返回键–>退出了Activity。

原因

下面我们追踪一下代码调用,找找产生这种现象的原因:

Fragment 3.0getActivity().onBackPressed()

Activity类

public void onBackPressed() {
if (mActionBar != null && mActionBar.collapseActionView()) {
return;
} if (!mFragments.getFragmentManager().popBackStackImmediate()) {
finishAfterTransition();
}
}

Fragment V4getActivity().onBackPressed()

FragmentActivity

public void onBackPressed() {
if (!mFragments.getSupportFragmentManager().popBackStackImmediate()) {
supportFinishAfterTransition();
}
}

真相

从对代码调用的追踪,发现了真相。Fragment3.0FragmentV4

  1. Fragment3.0getActivity().onBackPressed()默认调用了ActivityonBackPressed()方法,方法里面使用的getFragmentManager()获取FragmentManager对象弹出栈内的Fragment3.0版的Fragment
  2. FragmentV4getActivity().onBackPressed()默认调用了FragmentActivityonBackPressed()方法,方法里面使用的getSupportFragmentManager()获取FragmentManager对象进行弹出栈内的FragmentV4版的Fragment

简单说就是Fragment3.0要放在继承了Activity的Activity中使用:

public class XXX_Activity extends Activity{
...
}

FragmentV4要放在继承了FragmentActivity的Activity中使用:

public class XXX_Activity extends FragmentActivity{
...
} //或者系统默认的 FragmentActivity 的子类 AppCompatActivity
public class XXX_Activity extends AppCompatActivity{
...
}

Fragment和Activity版本不匹配时

开发的时候,或许并不能达到Fragment版本和对应的Activity相匹配的理想状态,那么就有了下面的一个比较完善的解决方案:

解决方案:

使用其匹配的Activity类的onBackPressed()方法的代码重写所在的ActivityonBackPressed()方法:

FragmentV4配合继承了Activity的Activity中时:

XXX_Activity extends Activity

//使用FragmentActivity的onBackPressed()的代码覆盖
@Override
public void onBackPressed() {
if (!mFragments.getSupportFragmentManager().popBackStackImmediate()) {
supportFinishAfterTransition();
}
}

Fragment3.0配合继承了FragmentActivity的Activity中时:

XXX_Activity extends FragmentActivity(或者AppCompatActivity)

//使用Activity的onBackPressed()的代码覆盖
@Override
public void onBackPressed() {
if (mActionBar!=null&&mActionBar.collapseActionView()) {
return;
} if (!mFragments.getFragmentManager().popBackStackImmediate()) {
finishAfterTransition();
}
}

总结

由于当前 Android Studio 默认新建的 Activity 继承于 AppCompatActivity,所以建议大家使用FragmentV4进行开发,这样能省下不少麻烦,本系列还有一篇文章介绍Fragment3.0使用onAttach时的Bug,而这个对于FragmentV4则没有。

传送门:Android项目开发填坑记-Fragmen的onAttach方法

PS:

你可以关注的我GithubCSDN微博

Android项目开发填坑记-Fragment的onBackPressed的更多相关文章

  1. Android项目开发填坑记-Fragment的onAttach

    背景 现在Android开发多使用一个Activity管理多个Fragment进行开发,不免需要两者相互传递数据,一般是给Fragment添加回调接口,让Activity继承并实现. 回调接口一般都写 ...

  2. Android项目开发填坑记-so文件引发的攻坚战

    故事的最初 我负责的项目A要求有播放在线视频的功能,当时从别人的聊天记录的一瞥中发现百度有相关的SDK,当时找到的是Baidu-T5Player-SDK-Android-1.4s,项目中Demo的so ...

  3. Android项目开发填坑记-9patchPng报错

    如果阅读体验不佳,请使用–> Github版 背景 之前写了一篇文章Android必知必会–NinePatch图片制作详细介绍了Android 9Patch图片的制作和一些Demo展示,这次说明 ...

  4. Java web 开发填坑记 2 -如何正确的创建一个Java Web 项目

    转载请标明出处:http://blog.csdn.net/zhaoyanjun6/article/details/72566261 本文出自[赵彦军的博客] Java web 开发填坑记 1-如何正确 ...

  5. Java Web 开发填坑记- 如何正确的下载 Eclipse

    一直以来,做 Java web 开发都是用 eclipse , 可是到 eclipse 官网一看,我的天 http://www.eclipse.org/downloads/eclipse-packag ...

  6. UiAutomator2.0升级填坑记

    UiAutomator2.0升级填坑记 SkySeraph May. 28th 2017 Email:skyseraph00@163.com 更多精彩请直接访问SkySeraph个人站点:www.sk ...

  7. Appium+python自动化(十三)- 输入中文 - 一次填坑记(超详解)

    简介 无论你在哪里,在做什么都会遇到很多坑,这些坑有些事别人挖的,有些是自己挖的.别人挖的叫坑人,自己挖的叫自杀,儿子挖的叫坑爹.因此在做app自动化道路上也不会是一帆风顺的,你会踩很多坑,这些坑和你 ...

  8. 浅谈html5 video 移动端填坑记

    这篇文章主要介绍了浅谈html5 video 移动端填坑记,小编觉得挺不错的,现在分享给大家,也给大家做个参考.一起跟随小编过来看看吧 本文介绍了html5 video 移动端填坑记,分享给大家,具体 ...

  9. Android项目开发全程(四)-- 将网络返回的json字符串轻松转换成listview列表

    前面几篇博文介绍了从项目搭建到获取网络字符串,对一个项目的前期整体工作进行了详细的介绍,本篇接着上篇介绍一下怎么样优雅将网络返回的json字符串轻松转换成listview列表. 先上图,看一下效果. ...

随机推荐

  1. ●SPOJ LCS2Longest Common Substring II

    题链: http://www.spoj.com/problems/LCS2/题解: 后缀自动机. 对第一个串建立后缀自动机, 然后把后面的每个串分别与该串的自动机去匹配,求出相应的数组val*[s]: ...

  2. 【NOIP2004】虫食算

    Description 所谓虫食算,就是原先的算式中有一部分被虫子啃掉了,需要我们根据剩下的数字来判定被啃掉的字母.来看一个简单的例子: 43#9865#045 +. 8468#6633 444455 ...

  3. C++值传递与引用传递

    值传递:形参是对实参的拷贝,改变形参的值不会改变外部实参的值,从被调用的角度来说,值传递时单向传递(实参->形参),参数的值只能传入,不能传出. 当函数内部需要修改参数,并且不希望这个改变影响调 ...

  4. K-means聚类 的 Python 实现

    K-means聚类 的 Python 实现 K-means聚类是一个聚类算法用来将 n 个点分成 k 个集群. 算法有3步: 1.初始化– K 个初始质心会被随机生成 2.分配 – K 集群通过关联到 ...

  5. JMQ

    [京东技术]京东的MQ经历了JQ->AMQ->JMQ的发展,其中JQ的基于关系数据库,严格意义上讲称不上消息中间件,JMQ的存储是JFS和HBase,AMQ即ActiveMQ,本文说说JM ...

  6. 图解JavaScript原型和原型链

    先看看最简单的栗子: //构造函数 function People(name, age){ this.name = name; this.age = age; } //原型对象(所有由构造函数实例而来 ...

  7. RandomAccessFile读取文本简介

    RandomAccessFile类的常用的操作方法 1.public  RandomAccessFile(File file, String mode)throws FileNotFoundExcep ...

  8. Intellij IDEA自动编译问题

    对IDEA的界面很有爱,但是感到他的项目启动速度太慢了.所以查了资料做了优化. 1:开启自动测试 File->setting->compiler 勾选上上面的,     2修改run/de ...

  9. 605. Can Place Flowers

    Suppose you have a long flowerbed in which some of the plots are planted and some are not. However, ...

  10. vim 基本命令入门

    简介 vim是Linux 系统下类似于Windows的记事本的编辑器. vim 中经常使用的三种模式 一般模式:浏览文件内容. 插入模式:编辑文件内容. 底行模式:进行保存编辑内容,退出等操作. 基本 ...