这篇文章分为两个步骤,一是代码修改,二是串口调试。
代码修改
Android键值底层驱动实现,各个方案商都不一样,一般而言,在改动的时候会有文档可以参考。本博客从在Android层添加一个键值开始讲起
kl文件
kl文件的作用是把底层传上来的键值映射为Android键值,一般情况下,文件内容如下
key 233 CUSTOM_KEYCODE
第一列表示这行是普通的键值,第二列是linux键值,第三列是Android键名
接下来就要找在哪个文件下添加kl文件
kl文件的命名
kl文件的命名是有规律可循的,每一个设备都会有一个Vendor ID 和一个Product ID 这是由设备厂商命名的,一般来说文件会被命名为如下所示内容,注意最后的Product ID:xxxx不能是0
Vendor_xxxx_Product_xxxx.kl
kl文件的优先级
按照Android标准,kl文件设备中如下所示顺序查找对应关系
/system/usr/keylayout/Vendor_XXXX_Product_XXXX_Version_XXXX.kl
/system/usr/keylayout/Vendor_XXXX_Product_XXXX.kl
/system/usr/keylayout/DEVICE_NAME.kl
/data/system/devices/keylayout/Vendor_XXXX_Product_XXXX_Version_XXXX.kl
/data/system/devices/keylayout/Vendor_XXXX_Product_XXXX.kl
/data/system/devices/keylayout/DEVICE_NAME.kl
/system/usr/keylayout/Generic.kl
/data/system/devices/keylayout/Generic.kl
一般来说kl文件由厂家提供,但是有一些无良厂家不想修改,如果键值不冲突,可以直接在Generic.kl文件中更改
Generic.kl文件在代码中的位置为
./framewprk/base/data/keyboards/Generic.kl
添加自定义的kl文件
kl文件可以通过device.mk文件直接配置到系统中,具体的代码类似如下
PRODUCT_COPY_FILES += $(DEVICE_FOLDER)/configs/Vendor_000d_Product_0001.kl:/system/usr/keylayout/Vendor_000d_Product_0001.kl
InputEventLabel.h文件
这个文件按照流程应该是第一个修改的才对,但是因为kl文件太重要了,所以第一个介绍。
InputEventLabel.h文件的位置为
./frameworks/native/include/input/InputEventLabels.h
InputEventLabel.h定义的是kl文件中的第三列,具体就是在KEYCODES数组中添加对应的值
#define DEFINE_KEYCODE(key) { #key, AKEYCODE_##key }
static const InputEventLabel KEYCODES[]
按照之前在kl文件中加的,我们在数组中添加如下所示内容即可
DEFINE_KEYCODE(CUSTOM_KEYCODE),
keycodes.h文件
这个文件映射的是Android中的键值,这个键值和InputEventLabel.h文件中数组添加的键名有一个映射关系,Android也是借此实现了从Linux键值到Android键值的映射
修改这个文件很简单,只要在enum中添加如下值就好了
AKEYCODE_CUSTOM_KEYCODE = 933
也就是键名添加AKEYCODE_;后面等于想映射的Android键值
KeyEvent.java
这个文件是最后一步,Andriod借此文件把键值从c语言转到java语言。
此文件的位置在:
./framework/base/core/java/android/view/KeyEvent.java
修改方法为在KeyEvent.java文件中添加静态常量
public static final int KEYCODE_CUSTOM_KEYCODE = 933;
变量名字与keycodes.h中比较少了开头的A,键值保持不变。
调试
调试命令dumpsys input,getevent,input keyevent 就够用了。
dumpsys input
这个命令可以查看到输入设备映射到了哪一个kl文件
当然这个命令的用处不止于此,不过我是用来验证哪一个kl文件的。
getevent
这个命令可以查看到输入的具体键值时多少
如图所示的例子中,是两个不同设备的输入相同键值,0x6c转换为10进制就是108,这个键值可以在kl文件中找到对应的Android键名,从而在KeyEvent.java文件中找到Android键值
input keyevent
这个命令是用来从串口输入键值的,有一段时间没有遥控器,就用这个方法凑活debug了
input keyevent 933
注意,输入的键值时Andriod键值