Android Input系统添加自定义键值上报实现(from Linux to Android)

系统环境

博主已在Android 7.0上验证成功,其他后6.0,8.0,9.0应该改动不大,可以直接拿过来使用,底层基本不变,上层Android可能会有些接口调整,不过万变不离其中,也是可以参考的。

Demo原理

博主实现的Demo主要是通过外部串口来发送音量调整数据,给到Android,Android端的serial_comm进程会不断处理串口接收到的信息,然后再通过驱动进行InputEvent上报,触发PhoneWindowManager对上报的自定义按键进行处理,从而调整音量数据。这样处理通过InputEvent上报处理比较及时迅速。

Android系统层

Android上层需要修改这些文件,我直接diff出来了,其中我们新增的键值要注意不要跟系统的重复:KEYCODE_SPECIFIC_VOLUME = 280

diff --git a/android/frameworks/base/core/java/android/view/KeyEvent.java b/android/frameworks/base/core/java/android/view/KeyEvent.java
index b003f00..fabce16 100755
--- a/android/frameworks/base/core/java/android/view/KeyEvent.java
+++ b/android/frameworks/base/core/java/android/view/KeyEvent.java
@@ -809,6 +809,9 @@ public class KeyEvent extends InputEvent implements Parcelable {
   
     public static final int KEYCODE_COPY = 278;
     /** Key code constant: Paste key. */
     public static final int KEYCODE_PASTE = 279;
+
+    public static final int KEYCODE_SPECIFIC_VOLUME = 280;
+
     /** Key code constant: a shortcut key for mouse */
     public static final int KEYCODE_MOUSE           = 10009;
     public static final int KEYCODE_TV_SYSTEM       = 10000;
diff --git a/android/frameworks/base/core/res/res/values/attrs.xml b/android/frameworks/base/core/res/res/values/attrs.xml
index b61d6cf..4330802 100644
--- a/android/frameworks/base/core/res/res/values/attrs.xml
+++ b/android/frameworks/base/core/res/res/values/attrs.xml
@@ -1832,6 +1832,7 @@ i
         <enum name="KEYCODE_CUT" value="277" />
         <enum name="KEYCODE_COPY" value="278" />
         <enum name="KEYCODE_PASTE" value="279" />
+        <enum name="KEYCODE_SPECIFIC_VOLUME" value="280" />
     </attr>
 
     <!-- ***************************************************************** -->
diff --git a/android/frameworks/native/include/android/keycodes.h b/android/frameworks/native/include/android/keycodes.h
index 4687b85..9fd76d5 100755
--- a/android/frameworks/native/include/android/keycodes.h
+++ b/android/frameworks/native/include/android/keycodes.h
@@ -758,6 +758,9 @@ enum {
   
     AKEYCODE_COPY = 278,
     /** Paste key. */
     AKEYCODE_PASTE = 279,
+
+    AKEYCODE_SPECIFIC_VOLUME = 280,
+
     // add for karaok by linjunqian
     AKEYCODE_MIC_VOLUME_UP   = 370,
     AKEYCODE_MIC_VOLUME_DOWN = 371,
diff --git a/android/frameworks/native/include/input/InputEventLabels.h b/android/frameworks/native/include/input/InputEventLabels.h
index 911c568..78ed509 100755
--- a/android/frameworks/native/include/input/InputEventLabels.h
+++ b/android/frameworks/native/include/input/InputEventLabels.h
@@ -319,6 +319,7 @@ static const InputEventLabel KEYCODES[] = {
   
     DEFINE_KEYCODE(CUT),
     DEFINE_KEYCODE(COPY),
     DEFINE_KEYCODE(PASTE),
+    DEFINE_KEYCODE(SPECIFIC_VOLUME),
     DEFINE_KEYCODE(MIC_VOLUME_UP),
     DEFINE_KEYCODE(MIC_VOLUME_DOWN),
     DEFINE_KEYCODE(KOUT_VOLUME_UP),
diff --git a/android/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java b/android/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java
index a4408fc..fbcd7e0 100644
--- a/android/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/android/frameworks/base/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -5530,6 +5530,20 @@ public class PhoneWindowManager implements WindowManagerPolicy {
   
                 break;
             }
 
+            case KeyEvent.KEYCODE_SPECIFIC_VOLUME: {
   
+                if (down) {
   
+                    Log.d(TAG, "KeyEvent.KEYCODE_SPECIFIC_VOLUME down");
+                    AudioManager audioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE);
+                    audioManager.setStreamVolume(AudioManager.STREAM_MUSIC,
+                            Integer.parseInt(SystemProperties.get("persist.sys.specific_volume")),
+                            AudioManager.FLAG_SHOW_UI);
+                    Log.d(TAG, "setStreamVolume " + SystemProperties.get("persist.sys.specific_volume"));
+                } else {
   
+                    Log.d(TAG, "KeyEvent.KEYCODE_SPECIFIC_VOLUME up");
+                }
+                break;
+            }
+
             case KeyEvent.KEYCODE_VOLUME_DOWN:
             case KeyEvent.KEYCODE_VOLUME_UP:
             case KeyEvent.KEYCODE_VOLUME_MUTE: {
   

到这里我们已经把上层的键值配好了,可以make systemimage -j8,烧进去进行测试,利用input keyevent 280,看看修改是否成功。

中间转换(Android - Linux)

Android自己定义了一套键值,Linux上报的键值需要通过kl文件转换才能正常识别。

diff --git a/android/frameworks/base/data/keyboards/Generic.kl b/android/frameworks/base/data/keyboards/Generic.kl
index 2a10bdd..ed9e1bd 100644
--- a/android/frameworks/base/data/keyboards/Generic.kl
+++ b/android/frameworks/base/data/keyboards/Generic.kl
@@ -247,6 +247,8 @@ key 224   BRIGHTNESS_DOWN
 key 225   BRIGHTNESS_UP
 key 226   HEADSETHOOK
 
+key 249   SPECIFIC_VOLUME
+
 key 256   BUTTON_1
 key 257   BUTTON_2
 key 258   BUTTON_3

Linux底层

从下面可以看到,我们再Linux层定义的键值为#define KEY_SPECIFIC_VOLUME 249,这里我写了个虚拟按键的驱动程序,echo 1 > /sys/kernel/virtual_key,在往virtual_key节点写1的时候就会上报KEY_SPECIFIC_VOLUME键,从而通知Android上层进行处理。

diff --git a/lichee/linux-3.10/include/uapi/linux/input.h b/lichee/linux-3.10/include/uapi/linux/input.h
index 74b5a00..5413c97 100644
--- a/lichee/linux-3.10/include/uapi/linux/input.h
+++ b/lichee/linux-3.10/include/uapi/linux/input.h
@@ -473,6 +473,8 @@ struct input_keymap_entry {
   
 
 #define KEY_MICMUTE        248    /* Mute / unmute the microphone */
 
+#define KEY_SPECIFIC_VOLUME    249
+
 #define KEY_VOICE_ASSIST 582
 /* Code 255 is reserved for special needs of AT keyboard driver */
diff --git a/lichee/linux-3.10/arch/arm64/configs/sun50iw6p1smp_android_7.x_defconfig b/lichee/linux-3.10/arch/arm64/configs/sun50iw6p1smp_android_7.x_defconfig
index 6d0ccaa..cc15e9a 100644
--- a/lichee/linux-3.10/arch/arm64/configs/sun50iw6p1smp_android_7.x_defconfig
+++ b/lichee/linux-3.10/arch/arm64/configs/sun50iw6p1smp_android_7.x_defconfig
@@ -1287,6 +1287,7 @@ CONFIG_INPUT_EVDEV=y
 CONFIG_INPUT_KEYRESET=y
 CONFIG_INPUT_KEYCOMBO=y
 # CONFIG_INPUT_POWERKEY is not set
+CONFIG_INPUT_VIRTUALKEY=y
 CONFIG_INPUT_SW_DEVICE=m
 
 #
diff --git a/lichee/linux-3.10/drivers/input/Kconfig b/lichee/linux-3.10/drivers/input/Kco
  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

甜牛奶蛋糕

你的鼓励将是我创作的最大动力

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

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

打赏作者

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

抵扣说明:

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

余额充值