GUI 输入设备补充说明
SDK 支持多种输入设备,其中以下几种输入设备,在 HoneyGUI 框架有相应的输入子系统支持:触摸板、键盘、滚轮。HoneyGUI 文档已对输入子系统以及移植说明有了一些介绍,可参考 GUI 输入子系统 。
本文对输入设备的移植、相关算法、输入设备的事件响应进行补充介绍。
触摸板
Module Touch
在
module_touch_common.c
中定义了 触摸板的一些通用行为,例如设备初始化、中断服务函数实现、获取数据接口实现等。在
touch_xxxx.c
中定义了不同 touch driver 的读写实现。在调用过
touch_driver_init()
初始化 touch 设备后,touch 的信息首先会被中断响应到TOUCH_INT_HANDLER
。-
中断服务函数需要调用
rtk_touch_hal_read_all()
收集 touch 原始数据,并填入TOUCH_DATA
结构体。原始数据包括初次 touch 和当前 touch 坐标信息以及时间戳等。
TOUCH_DATA
信息是通过get_raw_touch_data()
接口获取。
同时,一个 OS timer 会启动,用于监控 touch 行为是否结束,Timeout 参数是通过
touch_set_timeout_ms()
设定的。
GUI 移植
port_touchpad_get_data()
:该函数会调用get_raw_touch_data()
,获取TOUCH_DATA
并传递给gui_touch_port_data_t
。gui_indev
结构体的初始化:主要是 port 接口的注册,和长按、短按、滑动、抬手等行为的时间设定。gui_port_indev_init()
中还要设定抬手时间(touch_timeout_ms
),时间需要和 module touch 的 OS timer timeout 一致。
GUI 触摸板算法
SDK 使用 tp_algo_v2.c
作为 GUI Touch 算法,该版本主要是解耦了 触摸板数据更新对于 GUI 服务器任务运行的依赖。
触摸板算法函数 tp_algo_process()
会在 GUI 服务器任务运行的较早时期调用,并在经过计算后,填入坐标信息、事件类型等数据到 touch_info_t
结构体。
GUI 触摸板事件响应
结构体
touch_info_t
通常在控件的 draw prepare 过程中调用tp_get_info()
获取,然后根据获取到的触摸信息上报不同的 event 给控件。随后调用
gui_obj_event_set()
设定当前控件在当前帧需要响应的事件。GUI 上层应用需要通过
gui_obj_add_event_cb()
接口来绑定事件和回调函数。在控件 draw end 过程中,这些事件将会被收集并在所有控件的 draw end 过程完成后依次响应。
备注
gui_obj_add_event_cb()
接口通常会被 GUI 控件封装成具有具体行为意义的 API,推荐使用 GUI 控件的 API 完成事件和回调函数的绑定。一些控件例如窗帘、选项卡等控件,会实时响应 touch 行为,这些行为通常会在控件的 draw prepare 过程进行处理。
代码示例
在该示例中,创建一个 win 控件,通过 gui_win_long()
把 win_benchmark_start_cb()
和长按行为进行绑定,
实现在 win 界面长按执行 app_benchmark_start()
。
static void prepare(gui_obj_t *obj) { touch_info_t *tp = tp_get_info(); gui_win_t *this = (void *)obj; ... case TOUCH_LONG: { if (this->long_flag == false) { this->long_flag = true; gui_obj_event_set(obj, GUI_EVENT_TOUCH_LONG); } } break; ... } static void win_benchmark_start_cb(void *obj, uint16_t event, void *param) { switch (event) { case GUI_EVENT_TOUCH_LONG: { app_benchmark_start(); } break; ... } } void design_tab_benchmark_main(void *parent) { ... gui_win_t *win = gui_win_create(parent, "win_benchmark_main", 0, 0, 0, 0); gui_win_long(win, win_benchmark_start_cb, NULL); ... }
键盘
GUI 移植
port_kb_get_data()
:该函数将T_GPIO_KEY
结构体进行简单处理后,传递给kb_port_data
结构体。gui_indev
结构体的初始化:主要是 port 接口的注册,和长按、短按行为的时间设定。
GUI 键盘算法
SDK 使用 kb_algo.c
键盘算法,该算法和 tp_algo_v2.c
类似,算法函数 kb_algo_process()
会在 GUI 服务器任务运行的较早时期调用,
并在经过计算后将按键的状态信息、事件类型等数据存储到 kb_info_t
结构体中。
GUI 键盘事件响应
结构体
kb_info_t
通常在控件的 draw prepare 过程,调用kb_get_info()
获取,然后根据获取到的按键信息上报不同的 event 给控件。随后调用
gui_obj_event_set()
设定当前控件在当前帧需要响应的事件。GUI 上层应用需要通过
gui_obj_add_event_cb()
接口来绑定事件和回调函数。在控件的 draw end 过程中,这些事件将会被收集并在所有控件的 draw end 过程完成后依次响应。EVB 上的 KEY1 按键用于 LCD 唤醒功能,为了保证唤醒的实时性,采用在消抖函数直接发消息给 GUI task 的方式处理,唤醒
gui_wake_up_by_button()
。
滚轮
Module QDEC
module_qdec.c
定义了 QDEC 的一些行为,包括初始化,中断服务函数等。QDEC_Handler
中断服务函数,通过调用QDEC_GetAxisDirection
来获取 qdec 外设的数据,并存储到T_QDEC_DATA
结构体中,qdec_read_data()
接口用于获取T_QDEC_DATA
结构体的数据。
GUI 移植
port_wheel_get_data()
:该函数将T_GPIO_KEY
结构体进行简单处理后,传递给wheel_port_data
结构体。gui_indev
结构体的初始化:主要是 port 接口的注册。port_wheel_reset_prev_count()
:用于息屏后一些计数的重置。
GUI 滚轮算法
SDK 使用 wheel_algo.c
滚轮算法,该算法和 tp_algo_v2.c
类似,算法函数 wheel_algo_process()
会在 GUI 服务器任务运行的较早时期被调用,
并在经过计算后把 滚轮移动步数、状态信息、事件类型等数据存储到 touch_info_t
结构体中。
GUI 滚轮事件响应
结构体
touch_info_t
通常在控件的 draw prepare 过程调用wheel_get_info()
获取,然后根据获取到的信息上报不同的 event 给控件。随后调用
gui_obj_event_set()
设定当前控件在当前帧需要响应的事件。GUI 上层应用需要通过
gui_obj_add_event_cb()
接口来绑定事件和回调函数。在控件的 draw end 过程中,这些事件将会被收集并在所有控件的 draw end 过程完成后依次响应。目前 perspective 控件和 page 控件,支持 滚轮的一些简单操作。