BT手柄按键失灵的问题(1)

文章详细分析了蓝牙手柄在部分Android应用中的输入问题,特别是确定键在特定Activity中无法正常工作的情况。通过对比正常与异常情况下的事件流,以及深入分析InputReader和InputDispatcher的日志,揭示了问题可能与特定布局属性相关。解决方案包括修改相关配置文件,确保按键能够正确映射到预期功能。
摘要由CSDN通过智能技术生成

最近遇到一个问题,某些2.4G Input设备(应该是扫描按键设备,还包括BT手柄),进入到某些Activity之后,返回/确定按键失效 。

蓝牙手柄上的X和B键是复用的,在输入的时候X按下发挥确认键的功能,B则被解析为返回键。
进入某些Activity之后,X键和B键失去了复用功能,不能被解析为确认和返回,此时蓝牙手柄除了上下左右,其他的键功能基本丧失。


分析流程如下,

1,从Kernel的打印来看,正常和异常的时候,上传的数据完全一样。

从getevent来跟踪,按下手柄的确定键,也就是说按次键会有两个键值上报。

对上层能够报两个键值(DPAD_CENTER和BUTTON_X):
/dev/input/event6: 0004 0004 000900b9
/dev/input/event6: 0004 0004 000900b8
/dev/input/event6: 0004 0004 00090004 //这3个是一个MSC事件,是scan(#define MSC_SCAN 0x04 ),这三个扫描键对应的键值是DPAD_CENTER
/dev/input/event6: 0001 0133 00000001 //这一个KEY类型的事件(#define EV_KEY 0x01 ),键值为BUTTON_X(#define BTN_X 0x133 ),Value为按下
/dev/input/event6: 0000 0000 00000000 //SYNC信号

/dev/input/event6: 0004 0004 000900b9
/dev/input/event6: 0004 0004 000900b8
/dev/input/event6: 0004 0004 00090004
/dev/input/event6: 0001 0133 00000000
/dev/input/event6: 0000 0000 00000000 //对应的是抬起

2,InputReader和InputDispatcher的打印对比:
只有的对应的eventTime 不一样,其它的参数一致。
正常的时候:
D/InputReader( 5681): BatchSize: 5 Count: 5
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b9 when=164199285971000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b8 when=164199285971000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x00090004 when=164199285971000
D/InputReader( 5681): Input event: device=7 type=0x0001 code=0x0133 value=0x00000001 when=164199285971000
E/InputReader( 5681): >>>koffu,key dwon,keyDownIndex = -1 , policyFlags = 0
E/InputReader( 5681): ,metaStateChanged = 0
D/InputReader( 5681): Input event: device=7 type=0x0000 code=0x0000 value=0x00000000 when=164199285971000
D/InputDispatcher( 5681): notifyKey - eventTime=164199285971000, deviceId=7, source=0x501, policyFlags=0x0, action=0x0, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, downTime=164199285971000
D/InputDispatcher( 5681): dispatchKey - eventTime=164199285971000, deviceId=7, source=0x501, policyFlags=0x42000000, action=0x0, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, repeatCount=0, downTime=164199285971000
D/InputReader( 5681): BatchSize: 5 Count: 5
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b9 when=164199465804000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b8 when=164199465804000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x00090004 when=164199465804000
D/InputReader( 5681): Input event: device=7 type=0x0001 code=0x0133 value=0x00000000 when=164199465804000
E/InputReader( 5681): >>>koffu,key up,keyDownIndex = 0
E/InputReader( 5681): ,metaStateChanged = 0
D/InputReader( 5681): Input event: device=7 type=0x0000 code=0x0000 value=0x00000000 when=164199465804000
D/InputDispatcher( 5681): notifyKey - eventTime=164199465804000, deviceId=7, source=0x501, policyFlags=0x0, action=0x1, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, downTime=164199285971000
D/InputDispatcher( 5681): dispatchKey - eventTime=164199465804000, deviceId=7, source=0x501, policyFlags=0x42000000, action=0x1, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, repeatCount=0, downTime=16419928597100

不正常的时候:
D/InputReader( 5681): BatchSize: 5 Count: 5
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b9 when=164463524127000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b8 when=164463524127000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x00090004 when=164463524127000
D/InputReader( 5681): Input event: device=7 type=0x0001 code=0x0133 value=0x00000001 when=164463524127000
E/InputReader( 5681): >>>koffu,key dwon,keyDownIndex = -1 , policyFlags = 0
E/InputReader( 5681): ,metaStateChanged = 0
D/InputReader( 5681): Input event: device=7 type=0x0000 code=0x0000 value=0x00000000 when=164463524127000
D/InputDispatcher( 5681): notifyKey - eventTime=164463524127000, deviceId=7, source=0x501, policyFlags=0x0, action=0x0, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, downTime=164463524127000
D/InputDispatcher( 5681): dispatchKey - eventTime=164463524127000, deviceId=7, source=0x501, policyFlags=0x42000000, action=0x0, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, repeatCount=0, downTime=164463524127000
D/InputReader( 5681): BatchSize: 5 Count: 5
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b9 when=164463749112000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x000900b8 when=164463749112000
D/InputReader( 5681): Input event: device=7 type=0x0004 code=0x0004 value=0x00090004 when=164463749112000
D/InputReader( 5681): Input event: device=7 type=0x0001 code=0x0133 value=0x00000000 when=164463749112000
E/InputReader( 5681): >>>koffu,key up,keyDownIndex = 0
E/InputReader( 5681): ,metaStateChanged = 0
D/InputReader( 5681): Input event: device=7 type=0x0000 code=0x0000 value=0x00000000 when=164463749112000
D/InputDispatcher( 5681): notifyKey - eventTime=164463749112000, deviceId=7, source=0x501, policyFlags=0x0, action=0x1, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, downTime=164463524127000
D/InputDispatcher( 5681): dispatchKey - eventTime=164463749112000, deviceId=7, source=0x501, policyFlags=0x42000000, action=0x1, flags=0x8, keyCode=0x63, scanCode=0x133, metaState=0x0, repeatCount=0, downTime=16446352412700



3,在ViewRootImpl的打印:

这是出错时候的确定键(只报一个值,而且是BUTTON_X,所以确定键没有作用)
I/System.out( 7044): >>>koffu processImmediately = true
V/ViewRootImpl( 7044): Sending input event to IME: KeyEvent { action=ACTION_DOWN, keyCode=KEYCODE_BUTTON_X, scanCode=307, metaState=0, flags=0x8, repeatCount=0, eventTime=165753574, downTime=165753574, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 99, realAction: false
I/System.out( 7044): >>>koffu processImmediately = true
V/ViewRootImpl( 7044): Sending input event to IME: KeyEvent { action=ACTION_UP, keyCode=KEYCODE_BUTTON_X, scanCode=307, metaState=0, flags=0x8, repeatCount=0, eventTime=165753754, downTime=165753574, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 99, realAction: true

这是正常时候的按确定键(报两个值(BUTTON_X和DPAD_CENTER) 正常)
I/System.out( 7791): >>>koffu processImmediately = true
V/ViewRootImpl( 7791): Sending input event to IME: KeyEvent { action=ACTION_DOWN, keyCode=KEYCODE_BUTTON_X, scanCode=307, metaState=0, flags=0x8, repeatCount=0, eventTime=168524925, downTime=168524925, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 99, realAction: false
I/System.out( 7791): >>>koffu processImmediately = false
V/ViewRootImpl( 7791): Sending input event to IME: KeyEvent { action=ACTION_DOWN, keyCode=KEYCODE_DPAD_CENTER, scanCode=307, metaState=0, flags=0x408, repeatCount=0, eventTime=168524925, downTime=168524925, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 23, realAction: false
I/System.out( 7791): >>>koffu processImmediately = true
V/ViewRootImpl( 7791): Sending input event to IME: KeyEvent { action=ACTION_UP, keyCode=KEYCODE_BUTTON_X, scanCode=307, metaState=0, flags=0x8, repeatCount=0, eventTime=168525183, downTime=168524925, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 99, realAction: true
I/System.out( 7791): >>>koffu processImmediately = false
V/ViewRootImpl( 7791): Sending input event to IME: KeyEvent { action=ACTION_UP, keyCode=KEYCODE_DPAD_CENTER, scanCode=307, metaState=0, flags=0x408, repeatCount=0, eventTime=168525183, downTime=168524925, deviceId=7, source=0x501 }
D/RemoteIME( 6847): keycode: 23, realAction: true

思路:

1,这种蓝牙输入设备在其它Activity里面切换都能正常。但唯独进入某些Activity界面才触发确定键无效。
是不是和某些Activity的一些Layout属性有关?

2,但使用IR遥控器又不会出问题。IR遥控器(EV_KEY)和蓝牙手柄输入设备(EV_MSC和EV_KEY)的类型不一样。


solution:

通过修改对应的kl文件,把两个键值全部解析为需要的功能键。

比如,当按下确定按键之后,把BUTTON_X的值也指向DPAD_CENTER.


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

可夫小子

感谢大佬!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值