读书人

不同的模式启动一个应用解决不重复启

发布时间: 2012-09-14 23:00:49 作者: rapoo

不同的方式启动一个应用,解决不重复启动相同的Activity的方式

Android 安装软件后执行“OPEN”引起的Intent血案(系统BUG)

编写:徐建祥(netpirate@gmail.com)

日期:2010/12/13

网址:http://www.anymobile.org

打开程序的入口有很多个:

shell 命令行运行;

Launcher待机界面执行;

状态通知栏运行;

桌面快捷方式运行;

软件中调用运行;

安装软件后执行“OPEN”运行!

前面几项,调用程序的代码如下(参考:com.android.Launcher/.Launcher.java):

?

view plaincopy to clipboardprint?
  1. Intent?intent?=?new?Intent(this,?TestActivity.class);??
  2. intent.setAction(Intent.ACTION_MAIN);??
  3. intent.addCategory(Intent.CATEGORY_LAUNCHER);??
  4. intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);??
  5. intent.addFlags(Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);??
  6. this.startActivity(intent);??
?

?

而安装软件后,点击“Open”调用的代码如下(参考:com.android.packageinstaller/.InstallAppDone.java):

?

view plaincopy to clipboardprint?
  1. Intent?intent?=?new?Intent(this,?TestActivity.class);??
  2. this.startActivity(intent);??
?

?

如果用户安装软件后立刻执行“Open”,运行程序后,按HOME键返回到后台,然后再通过别的几种方法运行程序,则会再起一个MAIN程序。这是因为Intent的处理机制是,先比较Activity,再比较Action、Flag、bnds。。。,前后两张方式的Action不一样,一个有LAUNCHER ACTION,一个没有,所以会认为是启动两个不同的INTENT。

目前只想到一个简单的处理方式:

程序入口MAIN程序:SplashActivity.java

程序原入口程序:LoginActivity.java

启动程序后,在状态通知栏上添加快捷通知,代码如下:

?

view plaincopy to clipboardprint?
  1. package?org.anymobile.test;??
  2. import?android.app.Activity;??
  3. import?android.app.Notification;??
  4. import?android.app.NotificationManager;??
  5. import?android.app.PendingIntent;??
  6. import?android.content.ComponentName;??
  7. import?android.content.Context;??
  8. import?android.content.Intent;??
  9. import?android.os.Bundle;??
  10. public?class?SplashActivity?extends?Activity??
  11. {??
  12. ????@Override??
  13. ????protected?void?onCreate(Bundle?savedInstanceState)??
  14. ????{??
  15. ????????super.onCreate(savedInstanceState);??
  16. ??????????
  17. ????????this.showNotification(this.getBaseContext(),?-1,?"Test?is?Running!",?"Test?Start?Up!");??
  18. ??????????
  19. ????????Intent?intent?=?this.getIntent();??
  20. ????????if?(intent.hasCategory(Intent.CATEGORY_LAUNCHER))??
  21. ????????{??
  22. ????????????intent?=?new?Intent(this,?TestActivity.class);??
  23. ????????????this.startActivity(intent);??
  24. ????????}??
  25. ????????else??
  26. ????????{??
  27. ????????????intent?=?new?Intent();??
  28. ????????????ComponentName?componentName?=?new?ComponentName(this,?SplashActivity.class);??
  29. ????????????intent.setComponent(componentName);??
  30. //??????????intent?=?new?Intent(this,?SplashActivity.class);??
  31. ??????????????
  32. ????????????intent.setAction(Intent.ACTION_MAIN);??
  33. ????????????intent.addCategory(Intent.CATEGORY_LAUNCHER);??
  34. ????????????intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);??
  35. ????????????intent.addFlags(Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);??
  36. ??????????????
  37. ????????????this.startActivity(intent);??
  38. ????????}??
  39. ??????????
  40. ????????this.finish();??
  41. ????}??
  42. ????public?void?showNotification(Context?context,int?iResIcon,String?sNotifybar,String?sNofitymsg)??
  43. ????{??
  44. ????????//?look?up?the?notification?manager?service??
  45. ????????NotificationManager?nm?=?(NotificationManager)context.getSystemService(Context.NOTIFICATION_SERVICE);??
  46. ????????//?The?details?of?our?fake?message??
  47. ????????CharSequence?from?=?"Test";??
  48. ????????CharSequence?message?=?sNofitymsg;??
  49. ??????????
  50. ????????Intent?intent?=?new?Intent();??
  51. ????????ComponentName?componentName?=?new?ComponentName(context,?TestActivity.class);??
  52. ????????intent.setComponent(componentName);??
  53. ??????????
  54. ????????intent.setAction(Intent.ACTION_MAIN);??
  55. ????????intent.addCategory(Intent.CATEGORY_LAUNCHER);??
  56. ????????intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);??
  57. ????????intent.addFlags(Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);??
  58. ??????????
  59. ????????PendingIntent?contentIntent?=?PendingIntent.getActivity(context,?0,?intent,?0);??
  60. ????????Notification?notification?=???
  61. ????????????new?Notification(iResIcon,sNotifybar,?System.currentTimeMillis());??
  62. ????????notification.flags?=?notification.flags?|?Notification.FLAG_ONGOING_EVENT;??
  63. ????????notification.defaults?=???
  64. ????????????/*Notification.DEFAULT_SOUND|*/Notification.DEFAULT_LIGHTS;??
  65. ????????notification.setLatestEventInfo(context,?from,?message,?contentIntent);??
  66. line-height: 18px; color: black; background-coandroid:launchMode="singleInstance"
    试试。android:launchMode="singleInstance"
    试试。
    谢谢,管用 3 楼 anjxue 2011-12-01 使用singleInstance这个方法太草率了。
    比如我们的根activity为A,给A设置singleInstance.
    当只有一个A时没有问题,但当A上面有其它Activity时,就有问题的,比如A上面有B,C
    这样当按home切回桌面,再次点击应用程序图标时,程序又返回到A而不是C!
    显然通常情况下我们想要回到C的。

    我也在寻找合适的解决办法。

读书人网 >移动开发

热点推荐