Android 监听 Home 键

Android 的 Home 比较特殊,不能像其他键 (如返回键) 那样直接用 onKeyDown 或 onKeyUp 来监听,需要用其他的方法来实现监听。

在 Home 键按下时,系统会发出一个广播,我们只需要注册一个 Receiver 来接收这个广播即可:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
public class HomeKeyReceiver extends BroadcastReceiver {
private static final String TAG = HomeKeyReceiver.class.getSimpleName();

/* extra from home key broadcase receiver */
private static final String SYSTEM_DIALOG_REASON_EXTRA = "reason";
/* press home key to go back to home */
private static final String SYSTEM_DIALOG_REASON_HOME_KEY = "homekey";
/* long press home key to show recent apps */
private static final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps";
/* (long) press home key to show assistant */
private static final String SYSTEM_DIALOG_REASON_ASSIST = "assist";
/* (long) press home key to lock */
private static final String SYSTEM_DIALOG_REASON_LOCK = "lock";

private Context mContext;
/* listeners used in this broadcast receiver */
private OnHomeKeyListener mOnHomeKeyListener;
private OnRecentAppListener mOnRecentAppListener;
private OnAssistListener mOnAssistListener;
private OnLockListener mOnLockListener;

public HomeKeyReceiver(Context context) {
mContext = context;
}

/**
* Interface definition for a callback to be invoked when the reason is "homekey".
*/
public interface OnHomeKeyListener {
void onKeypressed();
}

/**
* Interface definition for a callback to be invoked when the reason is "recentapps".
*/
public interface OnRecentAppListener {
void onKeypressed();
}

/**
* Interface definition for a callback to be invoked when the reason is "assist".
*/
public interface OnAssistListener {
void onKeypressed();
}

/**
* Interface definition for a callback to be invoked when the reason is "lock".
*/
public interface OnLockListener {
void onKeypressed();
}

@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(Intent.ACTION_CLOSE_SYSTEM_DIALOGS)) {
String reason = intent.getStringExtra(SYSTEM_DIALOG_REASON_EXTRA);
if (TextUtils.isEmpty(reason)) {
return;
}

switch (reason) {
case SYSTEM_DIALOG_REASON_HOME_KEY:
if (mOnHomeKeyListener != null) {
mOnHomeKeyListener.onKeypressed();
}
break;

case SYSTEM_DIALOG_REASON_RECENT_APPS:
if (mOnRecentAppListener != null) {
mOnRecentAppListener.onKeypressed();
}
break;

case SYSTEM_DIALOG_REASON_ASSIST:
if (mOnAssistListener != null) {
mOnAssistListener.onKeypressed();
}
break;

case SYSTEM_DIALOG_REASON_LOCK:
if (mOnLockListener != null) {
mOnLockListener.onKeypressed();
}
break;

default:
Log.d(TAG, "other reason: " + reason);
break;
}
}
}

/**
* Register a callback to be invoked when system dialog reason is "homekey".
*/
public void setOnHomeKeyListener(OnHomeKeyListener l) {
mOnHomeKeyListener = l;
}

/**
* Register a callback to be invoked when system dialog reason is "recentapps".
*/
public void setOnRecentAppListener(OnRecentAppListener l) {
mOnRecentAppListener = l;
}

/**
* Register a callback to be invoked when system dialog reason is "assist".
*/
public void setOnAssistListener(OnAssistListener l) {
mOnAssistListener = l;
}

/**
* Register a callback to be invoked when system dialog reason is "lock".
*/
public void setOnLockListener(OnLockListener l) {
mOnLockListener = l;
}

/**
* Register the home key boradcasr receiver.
*/
public void register() {
IntentFilter homeFilter = new IntentFilter(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
mContext.registerReceiver(this, homeFilter);
}

/**
* Unregister the home key boradcasr receiver.
*/
public void unregister() {
mContext.unregisterReceiver(this);
}

由于 home 键在不同手机上,长 / 短按有不同的效果,代码列举出常用的几种,其中 homekey 表示短按 home 键退到桌面。

简单使用:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
private HomeKeyReceiver mHomeKeyReceiver;

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

mHomeKeyReceiver = new HomeKeyReceiver(this);
mHomeKeyReceiver.setOnHomeKeyListener(new OnHomeKeyListener() {
@Override
public void onKeypressed() {
Log.d(TAG, "home key pressed");
}
});
}

@Override
protected void onResume() {
super.onResume();
mHomeKeyReceiver.register();
}

@Override
protected void onPause() {
super.onPause();
mHomeKeyReceiver.unregister();
}

注意:这个 Receiver 需要在 onResume 中注册,在 onPause 中注销。