2010-02-05 81 views

回答

0
android.text.method.KeyListener.onKeyDown([view],[text],KEYCODE_HOME,[event]) 

我不知道其他参数如何适应,甚至是如何实现以上,但信息是所有在keylistner documentation

但他们也提到在another page家庭钥匙总是回家,你不能改变这一点。所以如果你打算有某种“你确定要退出”的对话框,那是行不通的。

8

您无法捕获HOME事件并以任何方式拦截它。当用户按主页键时,他们将始终被带到设备的主屏幕。

如果您需要知道您的活动何时发送到背景,例如用户按住home键或back键,我会实现onStop()方法。

+2

不,那是不正确的。即使你的意思是在onPause(),这个答案难道不正确的 - 记住的onStop不能保证被调用,在所有。这些小小的“Android特定”让我心生疑虑。 : -/ – 2014-12-04 04:00:43

3

你可以写一个广播监听器和过滤器设置为

<category android:name="android.intent.category.HOME" /> 

从广播接收开始乌尔活动/通知活动。

+0

这是不可能的,因为它不是广播意图... – Renetik 2013-12-31 16:47:49

12

您可以通过Activity.onUserLeaveHint()检测HOME按钮。这种方法在两种情况下被调用;当用户按下HOME并且开始新的活动时。确保以某种方式区分两者。

+0

当用户按Home键时,如果当前活动是当前默认启动器,则不会调用它。 – arts777 2012-08-03 00:09:27

+1

当活动启动其他活动时也会调用它。 – Blackhex 2013-03-28 17:27:22

+0

我同意@Blackhex。 HTTP://计算器。com/questions/6612058/android-onbackpressed-onuserleavehint/8749061#8749061问题也是这样说的。所以,它现在不适用于所有情况。 – 2013-09-13 23:14:52

8

有没有正式的方式来通知“首页”按键。但是有一个非常简单的解决方法,让您的应用程序区分“主页”按键和导致活动停止的任何其他操作。

对于每个需要在“家”的执行某些操作按键让他们从包含该活动扩展类:

/**************************************** On Home **********************************/ 
private boolean leaveCalled = false; 

@Override 
public void startActivity(Intent intent) { 
    leaveCalled= true; 
    super.startActivity(intent); 
} 

@Override 
public void onBackPressed() { 
    leaveCalled = true; 
    super.onBackPressed(); 
} 

@Override 
protected void onStop() { 
    super.onStop(); 
    // Home button pressed 
    if(!leaveCalled) { 
     // Do whatever you like. 
    } 

    leaveCalled = false; 
} 

编辑

您还需要延长你的片段来自包含这个的父类。这是因为片段会以其他方式提供额外的路线,以预期而非“主页”的方式在应用中的活动之间切换。

@Override 
public void startActivity(Intent intent) { 
    getActivity().startActivity(intent); 
} 

EDIT 2

我越来越接近想着这是不是对付这种最简单的方法......你还需要添加onConfigurationChange =“方向”所有的你使用这种方法的活动。然后,你可以补充一点:

@Override 
public void onConfigurationChanged(Configuration newConfig) { 
    super.onConfigurationChanged(newConfig); 
    leaveCalled = true;      
    finish(); 
    startActivity(getIntent()); 
} 

编辑3

Urgh

@Override 
public void finish() { 
    leaveCalled = true; 
    super.finish(); 
} 
+0

这些都不行。活动的'onStop()'是'leaveCalled = false'的情况太多了,就像电话,活动从服务中启动等一样。 – Yeung 2014-08-05 03:41:36

+0

同意 - 但这与其他“解决方法”面临的问题相同赶上主页按钮。这不是包含在API中的东西。 – Graeme 2014-08-06 08:19:29

5

这是可以做到(uptil 2.3 ATLEAST)。测试Android 2.3.5版HTC WildFire-S。代码片段捕捉/禁用所有的控制键:

@Override 
public void onAttachedToWindow() { 
    super.onAttachedToWindow();   
    this.getWindow().setType(WindowManager.LayoutParams.TYPE_KEYGUARD); 


} 

public boolean onKeyDown(int keyCode, KeyEvent event) {  

    if(keyCode == KeyEvent.KEYCODE_HOME || keyCode == KeyEvent.KEYCODE_POWER || keyCode == KeyEvent.KEYCODE_BACK || keyCode == KeyEvent.KEYCODE_MENU || keyCode == KeyEvent.KEYCODE_SEARCH ) 
    { 

     Toast.makeText(getApplicationContext(),"You pressed a control button with keyCode : " + keyCode, Toast.LENGTH_SHORT).show(); 
     return false; 

    } 
    else 
    { 
     Toast.makeText(getApplicationContext(),"You pressed" + keyCode, Toast.LENGTH_SHORT).show(); 
    } 

    return true; 
} 

public boolean onKeyUp(int keyCode, KeyEvent event) {  

    if(keyCode == KeyEvent.KEYCODE_HOME || keyCode == KeyEvent.KEYCODE_POWER || keyCode == KeyEvent.KEYCODE_BACK || keyCode == KeyEvent.KEYCODE_MENU || keyCode == KeyEvent.KEYCODE_SEARCH ) 
    { 

     return false; 

    } 
    else 
    { 
     // Do nothing 
    } 

    return true; 
} 
-7
@Override 
public boolean onKeyDown(int keyCode, KeyEvent event) {  

    if(keyCode == KeyEvent.KEYCODE_HOME) 
    { 

     //The Code Want to Perform. 

    } 
}); 
+0

不起作用! – amiekuser 2013-07-02 12:24:35

+0

从Android 4.0或更高版本无法正常工作 – 2013-11-19 07:11:12

+1

很好的答案 - 作品像魅力! :D NOOOOOT :) – 2014-12-04 04:02:59

38

更新 [2015年8月]:为每JM Lord的评论,因为所需的设备和棒棒糖上面这个答案可能无法正常工作。见Alternative to getRunningTasks in Android L


虽然,它的一个老问题,但大部分的答案并没有为我在API级别17及以上的工作。我正在回答最后为我工作的东西。我尝试了很多方法,但没有一个像今天一样工作。我试着

Call method when home button pressed on android答案,

Detect home button press in android

Overriding the Home button - how do I get rid of the choice?。要点是家庭就像一个紧急逃生按钮。所以你不能覆盖它,但可以在某些方面检测它。

一些我试过(包括上面的答案)和没有工作是那些的:

  1. 在许多方面为 上述使用keyCode==KeyEvent.KEYCODE_HOME。现在,如果你阅读 KeyEvent.KEYCODE_HOME的文档,它说This key is handled by the framework and is never delivered to applications。所以它现在没有更多 有效。

  2. 我试过使用onUserLeaveHint()。该文件说:

    调用作为活动周期的一部分,当活动即将 去到后台,成为用户选择的结果。例如, 用户按Home键时,onUserLeaveHint()将被呼叫 ,但是当来电打电话时会导致呼叫中的动作 自动进入前台。

    与的问题是,当你从那里您所呼叫onUserleaveLint(), 因为是我的情况下,在活动范围内启动Activity ,该方法也被调用。有关更多信息,请参阅Android onBackPressed/onUserLeaveHint问题。所以它不确定 它只会通过按home键来调用。

  3. 打电话onStop()。当活动在现有活动之上并且完全覆盖活动时,也可以调用它。所以这也不行。

最后以下工作我:

How to check current running applications in Android?,你可以说,如果你是在长按home键显示近期的任务,然后将其发送到后台。

所以,在你的你在哪里试图检测按下home键的活动onPause(),您可以检查应用程序是否已发送到后台。

@Override 
public void onPause() { 
    if (isApplicationSentToBackground(this)){ 
     // Do what you want to do on detecting Home Key being Pressed 
    } 
    super.onPause(); 
} 

函数来检查你是否是最近被发送到后台应用程序:

public boolean isApplicationSentToBackground(final Context context) { 
    ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); 
    List<RunningTaskInfo> tasks = am.getRunningTasks(1); 
    if (!tasks.isEmpty()) { 
     ComponentName topActivity = tasks.get(0).topActivity; 
     if (!topActivity.getPackageName().equals(context.getPackageName())) { 
      return true; 
     } 
    } 
    return false; 
} 

感谢@idish用于指出不要忘记,包括以下权限您的清单:

<uses-permission android:name="android.permission.GET_TASKS" /> 

我不确定这是否有任何缺点,但它对我很好。希望有一天能帮助别人。 P:如果您在已使用FLAG_ACTIVITY_NO_HISTORY标志启动的活动中使用此方法,那么这将不会有用,因为它会检查最近的历史记录以确定是否点击了Home按钮。在活动

@Override 
protected void onUserLeaveHint() 
{ 
    super.onUserLeaveHint(); 
} 

http://developer.android.com/reference/android/app/Activity.html#onUserLeaveHint()

+0

今天帮了我:)这是一个很好的解决方案。非常感谢你。注意:不要忘记在清单中包含以下权限: idish 2013-08-09 22:37:39

+1

很高兴帮助。感谢您指出了这一点。我编辑了答案。 – 2013-08-09 22:43:09

+0

完美!谢谢Shobhit! – Rendy 2013-09-16 01:56:24

6

使用onUserLeaveHint()方法,我发现基于由@Springfeed建议此解决方案。现在的问题是相当通用的,注意,这个特殊的解决方案:

  • 上棒棒堂的工作,以及更低的Android版本(基于ActivityManager我的先例代码失败的棒棒糖)
  • 同时捕捉家庭和历史记录按钮
  • 如果活动本身被定义为家庭活动,则不会捕捉家庭活动 - 总是
  • 如果活动是多种家庭活动中的一种,或者根本没有活动,则会捕捉家庭活动。

此代码是在我的基地Activity类(其中的所有活动继承)

public boolean startingActivity = false; 

    @Override 
    protected void onUserLeaveHint() 
    { 
     if(startingActivity) 
     { 
      // Reset boolean for next time 
      startingActivity = false; 
     } 
     else 
     { 
      // User is exiting to another application, do what you want here 
      Log.i(TAG, "Exiting"); 
      ... 
     } 
    } 

    @Override 
    public void startActivity(Intent intent) 
    { 
     startingActivity = true; 
     super.startActivity(intent); 
    } 

    @Override 
    public void startActivityForResult(Intent intent, int requestCode) 
    { 
     startingActivity = true; 
     super.startActivityForResult(intent, requestCode); 
    } 

正如一些方法也可以使用应用程序上下文推出的意图,我定义我的应用程序类召开ContextWrapper切换布尔以及(注意,我要通过基类的静态访问我自己的应用程序的最上面的活动)。

public class MyContext extends ContextWrapper 
{ 

    public MyContext(Context base) 
    { 
     super(base); 
    } 

    @Override 
    public void startActivity(Intent intent) 
    { 
     BaseActivity activity = BaseActivity.getActivity(); 
     if(activity != null) 
     { 
      activity.startingActivity = true; 
     } 

     super.startActivity(intent); 
    } 

} 

如果有必要,可能还想覆盖startActivities(...)。

希望这有助于:)

+0

我找到最好的答案:) – Neo 2015-04-02 04:46:31

+1

但是,当我们移动到另一个活动时,此方法会回拨。如何区分为HOME按钮按下。谢谢 – sandeepmaaram 2016-01-21 07:09:19

0
public boolean isApplicationSentToBackground(final Context context) { 
     ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); 
     List<RunningTaskInfo> tasks = am.getRunningTasks(1); 
     if (!tasks.isEmpty()) { 
      ComponentName topActivity = tasks.get(0).topActivity; 
      if (!topActivity.getPackageName().equals(context.getPackageName())) { 
       return true; 
      } 
     } 
     return false; 
    } 



public void onPause() { 
    super.onPause(); 
    if(isApplicationSentToBackground(this)) 
    { 
     Log.i("Home", "Home Pressed..!"); 
    } 
} 
2