> 文档中心 > OpenHarmony TouchScreen 无法正常工作问题分析

OpenHarmony TouchScreen 无法正常工作问题分析

问题背景:

 将openharmony 2.2 3.0 3.1beta 移植到imx8q 和 芯驰X9H 平台, 多出现过屏幕点亮以后TouchScreen 无法正常工作.   也就是说在其他富设备平台上移植OH的时候也会大概率出现类似的问题,有必要对该问题的深层次原因进行分析.

网上有一种解决方案: 修改 /system/etc/udev/rules.d/touchscreen.rules , 将其中的"DRIVERS"属性改成 该平台touch driver name.   严格来讲 这个是 使能 OH touch必须的一步, 但很遗憾只有这一步并不能解决上面两个平台遇到的问题.

问题原因分析:

在指出具体原因之前,先简要梳理一下OH 事件分发路径.OH 在3.1Beta之前显示架构是基于weston, 在3.1Beta以后 应该更换成RenderService(RS). 两套显示架构采用的事件分发机制是不一样的,简要梳理如下:

A. Weston 版本的事件分发架构如下:

 

B. RS 版本的事件分发架构如下:

 

由上两个图可以看到, 两种分发机制的 一个明显不同点在于: 一个是由weston 进程 分发 ; 而另外一个 不经RS,而是由一个独立的进程mmi_service 进行分发. 或者类似于android里面的InputManagerService,事件的分发不经由显示架构SF.

明显的相同点有两个: 一个是 多是通过socket 进行事件的传递;  另一个是 事件的获取都是通过libinput 接口.

回到分析"不能touch"这个问题, 由上可知,两种分发机制多是基于udev 的, 所以 配置touchscreen.rules 是必须的一步, 为什么这个是必须的一步,原因在于: udev 会根据这个配置文件 和 系统中的设备信息做match, 如没有找到匹配的配置文件,不会调用udev_device_update_db 在 /data/udev/data 和 /data/udev/tags  里面生成相关设备的配置信息. 而这些配置信息是libinput 正常工作所必须的, 具体逻辑如下所显:

 

其中在udev_device_get_is_initialized 将通过udev_device_read_db 读取这些设备信息文件,如没有这些文件,udev_device_get_is_initialized 将返回0.  这将导致 device_added 无法执行到, 也就生成不了 seat 和对应的 evdev 对象.  而这些信息 是libinput 能否正常工作所需要的, libinput_get_event 就不能从事件数组里面获得事件.

解决办法:

需要让touch 可以正常工作,前提条件是在/data/udev里面需要存在相关设备信息文件, 也就是说 udev_device_update_db 必须被调用, 而该接口要被调用,依赖底层上报 NETLINK_KOBJECT_UEVENT,存在如下逻辑:

 

imx8q 不能工作是因为设备正常冷启动时候,udev 服务没有接收到NETLINK_KOBJECT_UEVENT 事件, 需要插拔下 屏幕数据线.

X9H 不能工作是因为底层不会上报  NETLINK_KOBJECT_UEVENT,即使插拔 数据线,同样不会上报. 解决的办法是在 /data/udev 里面构建相关设备信息文件. 需要构建的文件如下:

     A. /data/udev/data/+input:input0   ---- 这里的数字0 与 /dev/input/event0(有事件生成的节点)相同

B./data/udev/data/c13:64  ---- 这里文件名是由字符c+"cat /sys/class/input/event0/dev" 组成

C. /data/udev/tags/seat/+input:input0

A ,B 中两个文件里面的内容构建方法可以 拷贝 一个其他平台的, 具体内容可以修改成 平台具体的信息.

芯驰X9H  OH 3.1Beta 版本: