是否可以创建一个监听硬件按键按下的 Android 服务?
我想运行一个 Android 后台服务,该服务将充当主屏幕或手机休眠时的按键侦听器。这可能吗?
从半相关的在线示例中,我组合了以下服务,但收到错误“onKeyDown 对于类型服务未定义”。这是否意味着如果不重写启动器就无法完成,或者我是否遗漏了一些明显的东西?
public class ServiceName extends Service {
@Override
public void onCreate() {
//Stuff
}
public IBinder onBind(Intent intent) {
//Stuff
return null;
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if(event.getAction() == KeyEvent.ACTION_DOWN) {
switch(keyCode) {
case KeyEvent.KEYCODE_A:
//Stuff
return true;
case KeyEvent.KEYCODE_B:
//Stuff
return true;
//etc.
}
}
return super.onKeyDown(keyCode, event);
}
}
我意识到当你从主屏幕打字时,Android 默认使用搜索栏,但这确实只是为了一个非常特殊的用途。除了我之外,我真的不希望任何人想要这个。例如,我认为使用相机按钮唤醒手机会很好。
I'd like to run an Android background service that will act as a keylistener from the home screen or when the phone is asleep. Is this possible?
From semi-related examples online, I put together the following service, but get the error, "onKeyDown is undefined for the type Service". Does this mean it can't be done without rewriting Launcher, or is there something obvious I'm missing?
public class ServiceName extends Service {
@Override
public void onCreate() {
//Stuff
}
public IBinder onBind(Intent intent) {
//Stuff
return null;
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if(event.getAction() == KeyEvent.ACTION_DOWN) {
switch(keyCode) {
case KeyEvent.KEYCODE_A:
//Stuff
return true;
case KeyEvent.KEYCODE_B:
//Stuff
return true;
//etc.
}
}
return super.onKeyDown(keyCode, event);
}
}
I realize Android defaults to the search bar when you type from the home screen, but this really is just for a very particular use. I don't really expect anyone but me to want this. I just think it'd be nice, for example, to use the camera button to wake the phone.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
据我所知,KeyEvents 只能由 Activity 处理,因为它们是用户按键的界面。服务在后台运行,不会对用户输入做出反应。这也是编译器警告“onKeyDown 对于类型 Service 未定义”的原因。服务或其任何超类不实现 KeyEvent.Callback 接口。作为解决方法,您可以在
AndroidManifest.xml
中注册一个 Activity,以对某些系统通知(例如android.intent.action.SCREEN_ON
)做出反应。当按下电源按钮打开屏幕时,您的活动可以启动,初始化某种服务并返回后台。如果这就是你打算做的。请参阅Intent 文档了解可能的操作。希望有帮助...
As far as I know KeyEvents can only be handled by Activities as they are the interface to the user pressing the keys. Services run in the background and are not intended to react on user input. That's also the reason of your compiler warning "onKeyDown is undefined for the type Service". Service or any of it's Superclasses don't implement the KeyEvent.Callback interface. As a workaround you could register an Activity in your
AndroidManifest.xml
to react on certain system notifications such asandroid.intent.action.SCREEN_ON
. When the power button is pressed to turn on the screen your activity could be started, initializing a service of some kind and go back to the background. If that's what you intend to do. See Intent docs for possible Actions.Hope that helped...
KeyEvents 需要触发 Activity。因此,无法通过服务检测到硬件按键,因为服务没有主机活动。您可以要求一个 SystemOverlay,并创建一个透明的活动。但这种方法似乎不适用于 API 26+ 设备。
解决此问题的方法是通过 AccessibilityServices 设置观察者。这允许您全局检测硬件按键。
注意:将应用程序启用为辅助功能应用程序可能会导致重大安全问题,用户会对启用此功能持谨慎态度。因此,在您的应用程序对于您的应用程序将处理的数据可以对用户“透明”的情况下,这是可取的。
此方法适用于所有 API 21+ 设备,我尚未在低于此的设备上进行测试,因此它可能有效,也可能无效。
步骤:
使用以下选项创建 XML 文件
在清单中定义您的 AccessibilityService
创建 AccessibilityService 类
KeyEvents require an Activity to be triggered. Hence, hardware key presses can't be detected via Services,as Services do not have a host activity. You could ask for a SystemOverlay, and create a transparent Activity. But this approach doesn't seem to work on API 26+ devices.
A workaround for this would be set up an observer through AccessibilityServices. This allows you to globally detect hardware key presses.
Note: Enabling an app as an Accessibility App can lead to major security issues, and users would be wary of enabling this. So this would be advisable in situations where your application can be "transparent" to the user with regard to the data your app will be handling.
This method works for all API 21+ devices, I haven't tested on devices below this, so it may or may not work.
Steps:
Create an XML file, with the following options
Define your AccessibilityService in the Manifest
Create an AccessibilityService Class
这需要 Lollipop (v5.0/API 21) 或更高版本,并且只能检测音量键
它将覆盖音量键操作,因此可能不需要全局使用它。
This requires Lollipop (v5.0/API 21) or higher, and can only detect volume keys
It will override volume key action, so using it globally may not be desired.
虽然无法直接在服务中监听硬件按键,但有时您可以监听这些按键的效果。例如,此答案描述了如何推断音量因媒体音量变化而按下的按键。
While it is not possible to listen for hardware key presses directly in a service, you can sometimes listen for the effects of those key presses. For example, this answer describes how to infer volume key presses from changes in media volume.