首先大家应该先了解一种情况,就是Android在应用中是无法拦截Home键的,今天我们带大家看一下Home键的三种情况。
1、在应用中按下Home键的逻辑处理
当我们在应用中按下Home键时界面会启动到桌面,我们在frameworks\base\policy\src\com\Android\internal\policy\impl\PhoneWindowManager.Java类中可以看到其实现原理,其不外乎就是调用了以下代码。
Intent mHomeIntent;
mHomeIntent = new Intent(Intent.ACTION_MAIN, null);
mHomeIntent.addCategory(Intent.CATEGORY_HOME);
mHomeIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
startActivity(mHomeIntent);
- 1
- 2
- 3
- 4
- 5
- 6
- 1
- 2
- 3
- 4
- 5
- 6
创建一个启动到桌面的Intent。
2、在应用中监听Home键
在Android应用中如果想监听Home键可以使用广播机制,这个在源码中也有体现。
static public final String SYSTEM_DIALOG_REASON_KEY = "reason";
static public final String SYSTEM_DIALOG_REASON_GLOBAL_ACTIONS = "globalactions";
static public final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps";
static public final String SYSTEM_DIALOG_REASON_HOME_KEY = "homekey";
static public final String SYSTEM_DIALOG_REASON_ASSIST = "assist";
@Override
public void onReceive(Context arg0, Intent arg1) {
String action = arg1.getAction();
//按下Home键会发送ACTION_CLOSE_SYSTEM_DIALOGS的广播
if (action.equals(Intent.ACTION_CLOSE_SYSTEM_DIALOGS)) {
String reason = arg1.getStringExtra(SYSTEM_DIALOG_REASON_KEY);
if (reason != null) {
if (reason.equals(SYSTEM_DIALOG_REASON_HOME_KEY)) {
// 短按home键
Toast.makeText(arg0, "短按Home键", Toast.LENGTH_SHORT).show();
} else if (reason.equals(SYSTEM_DIALOG_REASON_RECENT_APPS)) {
// RECENT_APPS键
Toast.makeText(arg0, "RECENT_APPS", Toast.LENGTH_SHORT).show();
}
}
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
这样就可以监听Home的是否被按下。
3、在Frameworks层拦截Home键
在frameworks\base\policy\src\com\android\internal\policy\impl\PhoneWindowManager.Java文件中我们首先看一下interceptKeyBeforeDispatching()方法。
public long interceptKeyBeforeDispatching(WindowState win, KeyEvent event, int policyFlags) {
//......
if (keyCode == KeyEvent.KEYCODE_HOME) {
//......
handleShortPressOnHome();
}
}
//进入handleShortPressOnHome
private void handleShortPressOnHome() {
// If there's a dream running then use home to escape the dream
// but don't actually go home.
if (mDreamManagerInternal != null && mDreamManagerInternal.isDreaming()) {
mDreamManagerInternal.stopDream(false /*immediate*/);
return;
}
// Go home!
launchHomeFromHotKey();
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
进入launchHomeFromHotKey方法。
static public final String SYSTEM_DIALOG_REASON_KEY = "reason";
static public final String SYSTEM_DIALOG_REASON_GLOBAL_ACTIONS = "globalactions";
static public final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps";
static public final String SYSTEM_DIALOG_REASON_HOME_KEY = "homekey";
static public final String SYSTEM_DIALOG_REASON_ASSIST = "assist";
void launchHomeFromHotKey() {
if (isKeyguardShowingAndNotOccluded()) {
// don't launch home if keyguard showing
} else if (!mHideLockScreen && mKeyguardDelegate.isInputRestricted()) {
// when in keyguard restricted mode, must first verify unlock
// before launching home
mKeyguardDelegate.verifyUnlock(new OnKeyguardExitResult() {
@Override
public void onKeyguardExitResult(boolean success) {
if (success) {
try {
ActivityManagerNative.getDefault().stopAppSwitches();
} catch (RemoteException e) {
}
sendCloseSystemWindows(SYSTEM_DIALOG_REASON_HOME_KEY);
startDockOrHome();
}
}
});
} else {
// no keyguard stuff to worry about, just launch home!
try {
ActivityManagerNative.getDefault().stopAppSwitches();
} catch (RemoteException e) {
}
if (mRecentsVisible) {
// Hide Recents and notify it to launch Home
awakenDreams();
sendCloseSystemWindows(SYSTEM_DIALOG_REASON_HOME_KEY);
hideRecentApps(false, true);
} else {
// Otherwise, just launch Home
sendCloseSystemWindows(SYSTEM_DIALOG_REASON_HOME_KEY);
//启动Launcher界面
startDockOrHome();
}
}
}
- 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
- 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
以上方法可处理Home键的拦截操作,接下来我们进入startDockOrHome方法。
void startDockOrHome() {
if (OptConfig.LC_RAM_SUPPORT) {
try {
ActivityManagerNative.getDefault().startHomePre();
} catch (RemoteException re) {
}
}
awakenDreams();
Intent dock = createHomeDockIntent();
if (dock != null) {
try {
startActivityAsUser(dock, UserHandle.CURRENT);
return;
} catch (ActivityNotFoundException e) {
}
}
//intent的相关设置
mHomeIntent = new Intent(Intent.ACTION_MAIN, null);
mHomeIntent.addCategory(Intent.CATEGORY_HOME);
mHomeIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK
| Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
startActivityAsUser(mHomeIntent, UserHandle.CURRENT);
}
- 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
- 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
好啦,这里就对Home键进行简单的监听和拦截。
<div id="digg" articleid="55094816">
<dl id="btnDigg" class="digg digg_disable" onclick="btndigga();">
<dt>顶</dt>
<dd>0</dd>
</dl>
<dl id="btnBury" class="digg digg_disable" onclick="btnburya();">