Android中Home键的监听和代码操作程序Home键退出(实质没有退出而类似于最小化)

来源:互联网 发布:重庆行知小小学校招聘 编辑:程序博客网 时间:2024/05/10 15:50

一、Home键的监听

public class HomeWatcherReceiver extends BroadcastReceiver {    private static final String TAG = "HomeReceiver";    private static final String SYSTEM_DIALOG_REASON_KEY = "reason";    private static final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps";    private static final String SYSTEM_DIALOG_REASON_HOME_KEY = "homekey";    @Override    public void onReceive(Context context, Intent intent) {        String action = intent.getAction();        if (action.equals(Intent.ACTION_CLOSE_SYSTEM_DIALOGS)) {            String reason = intent.getStringExtra(SYSTEM_DIALOG_REASON_KEY);            Log.d(TAG, "reason: " + reason);            if (SYSTEM_DIALOG_REASON_HOME_KEY.equals(reason)) {                // 短按Home键                Log.d(TAG, "homekey");            }        }    }}

注册这个Receiver只能动态注册

private static void registerHomeKeyReceiver(Context context) {    Log.d(TAG, "registerHomeKeyReceiver");    mHomeKeyReceiver = new HomeWatcherReceiver();    final IntentFilter homeFilter = new IntentFilter(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);    context.registerReceiver(mHomeKeyReceiver, homeFilter);}private static void unregisterHomeKeyReceiver(Context context) {    Log.i(TAG, "unregisterHomeKeyReceiver");    if (null != mHomeKeyReceiver) {        context.unregisterReceiver(mHomeKeyReceiver);    }}

二、代码操作程序Home键退出
我们经常看到QQ程序虽然我们点击back退出了,但实际上它并没有退出,只是将该Activity置到了后台,跟操作了Home键一样。

方法一:其实我们的Home主界面也是一个Activity,所以,我们只需要在应用执行back操作之后,启动一下这个Home主界面,这样我们的程序就被置于后台,被这个Home主界面Activity覆盖。

 @Overridepublic void onBackPressed() {    super.onBackPressed();    Intent intent = new Intent(Intent.ACTION_MAIN);    intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);    intent.addCategory(Intent.CATEGORY_HOME);    startActivity(intent);}

这种方法会出现一个问题,如果手机上有多个桌面,那么当你启动这个Activity的时候,可能系统不会直接跳转到该Home桌面而是让你选你你要启动哪个桌面,所以使用这种方法会有一些问题。

方法二:我们的Activity有一个moveTasktoBack()方法,moveTasktoBack()就是说让进程activity栈在后台去运行,类似最小化。可以使用这个方法,不让我们的应用退出。

 @Overridepublic void onBackPressed() {    super.onBackPressed();    moveTasktoBack(true);}

三、Activity#onUserLeaveHint()和Activity#onUserInteraction()

/**    * Called as part of the activity lifecycle when an activity is about to go into the background as the result of user choice.    * For example, when the user presses the Home key, {@link #onUserLeaveHint} will be called, but   * when an incoming phone call causes the in-call Activity to be automatically brought to the foreground,    *{@link #onUserLeaveHint} will not be called on the activity being interrupted.    *   * 当用户的操作使一个activity准备进入后台时,此方法会像activity的生命周期的一部分被调用。例如,当用户按下Home键,   * Activity#onUserLeaveHint()将会被回调。但是当来电导致来电activity自动占据前台,Activity#onUserLeaveHint()将不会被回调。   */  

Activity#onUserLeaveHint()
用户手动离开当前activity,会调用该方法,比如用户主动切换任务,短按home进入桌面等。系统自动切换activity不会调用此方法,如来电,灭屏等。

onUserLeaveHint()作为activity周期的一部分,它在activity因为用户要跳转到别的activity而要退到background时使用。比如,在用户按下Home键,它将被调用。比如有电话进来(不属于用户的选择),它就不会被调用。
那么系统如何区分让当前activity退到background时使用是用户的选择?

它是根据促使当前activity退到background的那个新启动的Activity的Intent里是否有FLAG_ACTIVITY_NO_USER_ACTION来确定的。

注意:调用finish()使该activity销毁时不会调用该函数

/**   * Called whenever a key, touch, or trackball event is dispatched to the   * activity.  Implement this method if you wish to know that the user has   * interacted with the device in some way while your activity is running.   *   * <p>All calls to your activity's {@link #onUserLeaveHint} callback will   * be accompanied by calls to {@link #onUserInteraction}.   *   * activity无论分发按键事件、触摸事件或者轨迹球事件都会调用Activity#onUserInteraction()。   * 如果你想知道用户用某种方式和你正在运行的activity交互,可以重写Activity#onUserInteraction()。   * 所有调用Activity#onUserLeaveHint()的回调都会首先回调Activity#onUserInteraction()。   */  

Activity#onUserInteraction()
activity在分发各种事件的时候会调用该方法,注意:启动另一个activity,Activity#onUserInteraction()会被调用两次,一次是activity捕获到事件,另一次是调用Activity#onUserLeaveHint()之前会调用Activity#onUserInteraction()。

参考文章:
Activity#onUserLeaveHint()和Activity#onUserInteraction()

Activity启动模式 及 Intent Flags 与 栈 的关联分析

0 0