Yarn post graphics model Component HammerJS vue绑定点击事件 后台系统模板 bootstrap模板 nginx视频 mysql新增用户和权限 手动安装fastboot驱动 hbuilder插件 linux重启mysql mysql学习 python集合 python设置环境变量 java实例 java中的多态 java泛型 java中的接口 java类的继承 java中tostring方法 java如何获取当前时间 linux安装教程 网站数据分析工具 房产证生成器 高等数学同济第七版 快捷精灵 php正则匹配 js切割字符串 数据库编程软件 淘新闻下载 opencv是什么 极速pdf转word 组合索引 财务报表软件免费版 sai怎么复制图层 ps镂空字体怎么做 maya镜像复制
当前位置: 首页 > 学习教程  > 编程语言

Android9鼠标双屏控制实现

2020/8/11 20:35:49 文章标签:

首先上一张思维导图来简单梳理一下鼠标事件的上报,以及native层和java层的关联,以及InputManagerService和WindowManagerService的关联以及互调。

其实最初的关联是在SystemServer启动的时候实现,在实例化wm的时候将IMS传入如下代码:

wm = WindowManagerService.main(context, inputManager,
mFactoryTestMode != FactoryTest.FACTORY_TEST_LOW_LEVEL,
!mFirstBoot, mOnlyCore, new PhoneWindowManager());

并且IMS将wm中的InputMonitor作为回调传入,代码如下:

  inputManager.setWindowManagerCallbacks(wm.getInputMonitor());

通过回调我们可以从native层获取到java层的一些信息。

 

鼠标事件同其他输入事件的流程基本一致,都是从event事件中获取到信息,并通过InputReader.cpp来进行监听,然后处理相关的事件,比如按键,鼠标移动,和

鼠标经过等事件,然后通过dispatch将事件进行分发,再让上层处理。

 

我们实现双屏鼠标的思路是获取到双屏的显示id,然后根据id进行鼠标的绘制,以及事件的分发,其实在Android9已经默认支持副屏事件的鼠标处理,但是显示还不支持,

所以我们工作的重心在于如何在副屏绘制鼠标,已经鼠标动作的控制。

 

实现的方式参考windows的双屏控制,甩鼠标进行左右屏切换,可以通过判断鼠标拖动的力度来实现。

 

关于鼠标事件左右屏切换参考如下代码:


diff --git a/frameworks/native/services/inputflinger/InputReader.cpp b/frameworks/native/services/inputflinger/InputReader.cpp
old mode 100644
new mode 100755
index e0cd8a0..be87e6d
--- a/frameworks/native/services/inputflinger/InputReader.cpp
+++ b/frameworks/native/services/inputflinger/InputReader.cpp
@@ -2786,7 +2786,6 @@ void CursorInputMapper::sync(nsecs_t when) {
int32_t lastButtonState = mButtonState;
int32_t currentButtonState = mCursorButtonAccumulator.getButtonState();
mButtonState = currentButtonState;
-
bool wasDown = isPointerDown(lastButtonState);
bool down = isPointerDown(currentButtonState);
bool downChanged;
index e0cd8a0..be87e6d
--- a/frameworks/native/services/inputflinger/InputReader.cpp
+++ b/frameworks/native/services/inputflinger/InputReader.cpp
@@ -2786,7 +2786,6 @@ void CursorInputMapper::sync(nsecs_t when) {
int32_t lastButtonState = mButtonState;
int32_t currentButtonState = mCursorButtonAccumulator.getButtonState();
mButtonState = currentButtonState;
-
bool wasDown = isPointerDown(lastButtonState);
bool down = isPointerDown(currentButtonState);
bool downChanged;
@@ -2807,6 +2806,8 @@ void CursorInputMapper::sync(nsecs_t when) {
float deltaY = mCursorMotionAccumulator.getRelativeY() * mYScale;
bool moved = deltaX != 0 || deltaY != 0;

+ ALOGE("liangchao deltaX %f and deltaY %f",deltaX,deltaY);
+
// Rotate delta according to orientation if needed.
if (mParameters.orientationAware && mParameters.hasAssociatedDisplay
&& (deltaX != 0.0f || deltaY != 0.0f)) {
@@ -2832,11 +2833,26 @@ void CursorInputMapper::sync(nsecs_t when) {
mPointerVelocityControl.move(when, &deltaX, &deltaY);

int32_t displayId;
+
if (mSource == AINPUT_SOURCE_MOUSE) {
if (moved || scrolled || buttonsChanged) {
+ if(deltaX < -80.0){
+ pointerToSecond = false;
+ }else if(deltaX > 80.0){
+ pointerToSecond = true;
+ }else {
+ //displayId = ADISPLAY_ID_DEFAULT;
+ }
+ if(pointerToSecond){
+ displayId = getPolicy()->getPointerDisplayIdPolicy();
+ }else{
+ displayId = ADISPLAY_ID_DEFAULT;
+ }
+
+ mPointerController->setPointerDisplayId(displayId);
mPointerController->setPresentation(
PointerControllerInterface::PRESENTATION_POINTER);
-
+
if (moved) {
mPointerController->move(deltaX, deltaY);
}
@@ -2854,7 +2870,7 @@ void CursorInputMapper::sync(nsecs_t when) {
pointerCoords.setAxisValue(AMOTION_EVENT_AXIS_Y, y);
pointerCoords.setAxisValue(AMOTION_EVENT_AXIS_RELATIVE_X, deltaX);
pointerCoords.setAxisValue(AMOTION_EVENT_AXIS_RELATIVE_Y, deltaY);
- displayId = ADISPLAY_ID_DEFAULT;
+

通过判断鼠标移动的距离来决定鼠标事件的displayId.

 

还有就是鼠标的绘制具体的代码已经做成patch。

 


本文链接: http://www.dtmao.cc/news_show_100390.shtml

附件下载

相关教程

    暂无相关的数据...

共有条评论 网友评论

验证码: 看不清楚?