首页 > 其他分享 >tslib单点多点触摸(转载别人的如有侵权请联系删除)

tslib单点多点触摸(转载别人的如有侵权请联系删除)

时间:2023-07-19 11:33:34浏览次数:43  
标签:单点 struct int ts mt 触摸屏 tslib 侵权

第一:tslib库基本简介

    上篇文章为了获取触摸点,主要是对读取到的struct input_event类型数据进行分析,得到各个触摸点坐标。接下来,主要使用tslib库进行学习,这是Linux系统下,专门为触摸屏开发的应用层函数库。

     tslib库是开源的,也就是可以直接获取到tslib的源代码。tslib为触摸屏驱动和应用层之间的适配层,它把应用程序中读取触摸屏struct input_event类型数据(这是输入设备上报给应用层的原始数据)并进行解析的操作过程进行了封装,向使用者提供了封装好的API接口。tslib从触摸屏中获得原始的坐标数据,并通过一系列的去抖、坐标变换等操作,来去除噪声并将原始的触摸屏坐标转换为相应的屏幕坐标。

    tslib可以作为Qt的触摸屏输入插件,为Qt提供触摸输入支持,如果在嵌入式Linux硬件平台上开发过Qt应用程序应该知道,并不是只有 tslib 才能作为 Qt 的插件、为其提供触摸输入支持,还有很多插件都可以。

第二:tslib安装目录下的文件夹介绍

     进入到tslib安装目录下:

092e92fa-6366-11ed-8abf-dac502259ad0.png

     bin目录

     bin目录下有一些tslib提供的小工具,可以用于测试触摸屏,如下所示:

0959ae18-6366-11ed-8abf-dac502259ad0.png

     etc目录

     etc目录下有一个配置文件ts.conf,前面给大家提到过:

0979f6aa-6366-11ed-8abf-dac502259ad0.png

     打开ts.conf文件看看它有哪些配置选项:

099e96e0-6366-11ed-8abf-dac502259ad0.png

      module_raw input:取消注释,使能支持input输入事件;

module pthres pmin=1:如果我们的设备支持按压力大小测试,那么可以把它的注释取消,pmin 用于调节按压力灵敏度,默认就是等于 1。

module dejitter delta=100:tslib 提供了触摸屏去噪算法插件,如果需要过滤噪声样本,取消注释,默认参数 delta=100。

module linear:tslib 提供了触摸屏坐标变换的功能,譬如将 X、Y 坐标互换、坐标旋转等之类,如果我们需要实现坐标变换,可以把注释去掉。

这里就不去改动了,直接使用默认的配置就行了。

     include 目录

     include目录下只有一个头文件tslib.h,该头文件中包含了一些结构体数据结构以及API接口的声明,使用tslib提供的API就需要包含该头文件。

     lib目录

     lib目录下包含了编译tslib源码所得到的库文件,默认这些都是动态库文件,也可以通过配置tslib工程使其生成静态库文件;ts目录下存放的是一些插件库。

09e6b862-6366-11ed-8abf-dac502259ad0.png

第三:在开发板上测试tslib库

      使用tslib提供的API接口来编写触摸屏的应用程序,使用tslib库函数需要在我们的应用程序中包含tslib的头文件tslib.h,使用tslib编程其实非常简单,基本步骤如下所示:

       第一步打开触摸屏设备;

       第二步配置触摸屏设备;

       第三步读取触摸屏数据;

 1、打开触摸屏设备

      使用tslib提供的库函数ts_open打开触摸屏设备,其函数原型如下所示:

 

#include "tslib.h"
struct tsdev *ts_open(const char *dev_name,int nonblock);

 

      参数dev_name 指定了触摸屏的设备节点;参数nonblock表示是否以非阻塞方式打开触摸屏设备,如果nonblock等于0表示阻塞方式,如果为非0值则表示以非阻塞方式打开。

      调用成功返回一个struct sdev *指针,指向触摸屏设备句柄;如果打开设备失败,将返回NULL。除了使用ts_open()打开设备外,还可以使用ts_setup()函数,其函数原型如下所示:

 

#inlcude "tslib.h"

 

   参数 dev_name 指定触摸屏的设备节点,与 ts_open()函数中的 dev_name 参数意义相同;但对于 ts_setup()来说,参数 dev_name 可以设置为 NULL,当 dev_name 设置为 NULL 时,ts_setup()函数内部会读取TSLIB_TSDEVICE 环境变量,获取该环境变量的内容以得知触摸屏的设备节点。

     ts_setup()相比ts_open(),除了打开触摸屏设备外,还可以对触摸屏设备进行配置。

2、配置触摸屏设备

     调用ts_config()函数进行配置,其函数原型如下所示:

 

#include "tslib.h"
int ts_config(struct tsdev *ts)

 

     参数ts指向触摸屏句柄。

     成功返回0,失败返回-1。

     所谓配置其实指的就是解析ts.conf文件中的配置信息,加载相应的插件。

第四:读取触摸屏数据

     读取触摸屏数据使用 ts_read()或 ts_read_mt()函数,区别在于 ts_read 用于读取单点触摸数据,而ts_read_mt 则用于读取多点触摸数据,其函数原型如下所示:

 

#include "tslib.h"
int ts_read(struct tsdev *ts,struct ts_sample *samp,int nr)
int ts_read_mt(struct tsdev *ts, struct ts_sample_mt **samp, int max_slots, int nr)

 

      参数ts指向一个触摸屏设备句柄,参数nr表示对一个触摸点的采样数,设置为1即可。

      ts_read_mt()函数有一个 max_slots 参数,表示触摸屏支持的最大触摸点数,应用程序可以通过调用 ioctl()函数来获取触摸屏支持的最大触摸点数以及触摸屏坐标的最大分辨率等信息,稍后向大家介绍。

      ts_read()函数的 samp 参数是一个 struct ts_sample *类型的指针,指向一个 struct ts_sample 对象,struct ts_sample 数据结构描述了触摸点的信息;调用 ts_read()函数获取到的数据会存放在 samp 指针所指向的内存中。struct ts_sample 结构体内容如下所示:

 

struct ts_sample{
     int x;  //X坐标
     int y;  //Y坐标
     unsigned int pressure;  //按压力大小
     struct timeval  tv;   //时间
};

 

      ts_read_mt()函数的 samp 参数是一个 struct ts_sample_mt **类型的指针,多点触摸应用程序,每一个触摸点的信息使用 struct ts_sample_mt 数据结构来描述;一个触摸点的数据使用一个 struct ts_sample_mt 对象来装载,将它们组织成一个 struct ts_sample_mt 数组,调用 ts_read_mt()时,将数组地址赋值给 samp 参数。

     struct ts_sample结构体内容如下所示:

 

struct ts_sample_mt {
 /* ABS_MT_* event codes. linux/include/uapi/linux/input-event-codes.h
 * has the definitions.
 */
 int x; //X 坐标
 int y; //Y 坐标
 unsigned int pressure; //按压力大小
 int slot; //触摸点 slot
 int tracking_id; //ID
 int tool_type;
 int tool_x;
 int tool_y;
 unsigned int touch_major;
 unsigned int width_major;
 unsigned int touch_minor;
 unsigned int width_minor;
 int orientation;
 int distance;
 int blob_id;
 struct timeval tv; //时间
 /* BTN_TOUCH state */
 short pen_down; //BTN_TOUCH 的状态
 short valid;  //此次样本是否有效标志
 };

 

第五:单点触摸应用程序实现

 

#include 
#include 
#include     //包含tslib.h的头文件
int main(int argc, char *argv[])
{
 struct tsdev *ts = NULL;
 struct ts_sample samp;
 int pressure = 0;//用于保存上一次的按压力,初始为 0,表示松开
 /* 打开并配置触摸屏设备 */
 ts = ts_setup(NULL, 0);
 if (NULL == ts) {
 fprintf(stderr, "ts_setup error");
 exit(EXIT_FAILURE);
 }
 /* 读数据 */
 for ( ; ; ) {
 if (0 > ts_read(ts, &samp, 1)) {
 fprintf(stderr, "ts_read error");
 ts_close(ts);
 exit(EXIT_FAILURE);
 }
 if (samp.pressure) {//按压力>0
     if (pressure) //若上一次的按压力>0
     printf("移动(%d,%d)
",samp.x,samp.y);
     else
     printf("按下(%d,%d)
",samp.x,samp.y);
     }
     else
     printf("松开
");//打印坐标
     pressure = samp.pressure;
 }
 
     ts_close(ts);
     exit(EXIT_SUCCESS);
}

 

分析:利用代码直接打开、配置设备、接着读取数据,通过判断按压大小确定触摸的状态。

 

${CC} -I /home/dt/tools/tslib/include -L /home/dt/tools/tslib/lib -lts -o testApp testApp.c

 

0a1257b0-6366-11ed-8abf-dac502259ad0.png

    -I选项指定头文件的路径,也就是指定tslib安装目录下的include目录,如果不指定头文件路径,编译时将会找不到tslib.h头文件;-L 选项用于指定库文件的路径,也就是指定 tslib 安装目录下的 lib 目录;我们将 tslib 编译成了动态库文件,以库文件的形式提供,编译时需要链接到这些库文件;而-l 选项则用于指定链接库(也可写成-l ts,也就是 libts.so 库文件,Linux 中,动态库文件的命名方式为 lib+名字+.so)。

      将编译得到的可执行文件拷贝到开发板 Linux 系统的用户家目录下,执行应用程序,进行测试:

0a456844-6366-11ed-8abf-dac502259ad0.png

第六:多点触摸应用程序实现

    接下来基于tslib的多点触摸应用程序,使用ts_read_mt()函数读取多点触摸数据。

 

#include 
#include 
#include 
#include 
#include 


int main(int argc, char *argv[])
{
 struct tsdev *ts = NULL;
 struct ts_sample_mt *mt_ptr = NULL;
 struct input_absinfo slot;
 int max_slots;
 unsigned int pressure[12] = {0}; //用于保存每一个触摸点上一次的按压力,初始为 0,表示松开
 int i;
 /* 打开并配置触摸屏设备 */
 ts = ts_setup(NULL, 0);
 if (NULL == ts) {
 fprintf(stderr, "ts_setup error");
 exit(EXIT_FAILURE);
}
 /* 获取触摸屏支持的最大触摸点数 */
 if (0 > ioctl(ts_fd(ts), EVIOCGABS(ABS_MT_SLOT), &slot)) {
 perror("ioctl error");
 ts_close(ts);
 exit(EXIT_FAILURE);
 }
 max_slots = slot.maximum + 1 - slot.minimum;
 printf("max_slots: %d
", max_slots);
 /* 内存分配 */
 mt_ptr = calloc(max_slots, sizeof(struct ts_sample_mt));
 /* 读数据 */
 for ( ; ; ) {
 if (0 > ts_read_mt(ts, &mt_ptr, max_slots, 1)) {
 perror("ts_read_mt error");
 ts_close(ts);
 free(mt_ptr);
 exit(EXIT_FAILURE);
 }
 for (i = 0; i < max_slots; i++) {
 if (mt_ptr[i].valid) {//有效表示有更新!
 if (mt_ptr[i].pressure) { //如果按压力>0
 if (pressure[mt_ptr[i].slot])//如果上一次的按压力>0
 printf("slot<%d>, 移动(%d, %d)
", mt_ptr[i].slot, mt_ptr[i].x, mt_ptr[i].y);
 else
 printf("slot<%d>, 按下(%d, %d)
", mt_ptr[i].slot, mt_ptr[i].x, mt_ptr[i].y);
 }
 else
 printf("slot<%d>, 松开
", mt_ptr[i].slot);
 pressure[mt_ptr[i].slot] = mt_ptr[i].pressure;
 }
 }
 }
 /* 关闭设备、释放内存、退出 */ 
  ts_close(ts);
  free(mt_ptr);
  exit(EXIT_SUCCESS);
}

 

      整个思路与单点触摸应用程序相同,通过ts_read_mt()函数读取触摸点数据,将这些数据存放在 mt_ptr 数组中,接着在 for()循环中判断每一个触摸点数据是否有效,有效则表示该触摸点信息发生更新。

 

${CC} -I /home/dt/tools/tslib/include -L /home/dt/tools/tslib/lib -lts -o testApp testApp.c

 

0a698e5e-6366-11ed-8abf-dac502259ad0.png

 将编译得到的可执行文件复制到开发板Linux系统用户家目录下,执行程序:

0aacfedc-6366-11ed-8abf-dac502259ad0.png

总结:触摸屏在很多场合下都会使用到,掌握tslib库的使用方法,对未来个人的开发具有重要作用。

标签:单点,struct,int,ts,mt,触摸屏,tslib,侵权
From: https://www.cnblogs.com/linux-learn/p/17565127.html

相关文章

  • 高并发的哲学原理(七)-- 最难以解决的单点:数据库以及它背后的存储
    前面六篇文章,我们解决了web服务的百万QPS问题,从本文开始,我们将用三篇文章,尝试构建出百万QPS后端系统所需要的数据库。首先要明确,这里的数据库指的是关系型数据库,即满足ACID原则并用SQL语言进行操作的持久性(掉电数据不丢)数据库。当然,在追求高并发的过程中,我们将不可避免......
  • 实战:单点登录的两种实现方式,附源码
    相关课程最近工作有点忙,好久没更新文章了,正好这两天在整理单点登陆相关的文档,今天趁着小孩睡着了......
  • 微信小游戏代码包侵权解决办法
    微信过审机制介绍1、大致步骤就是提审->机器审核->人工审核;2、机器审核部分:审核代码部分,资源相关部分人工审核部分:审核UI相关,标题是否侵权,玩法是否符合类别3、审核时间:正常的账号在100分的情况下审核时间都会在2个小时内。审核细节1、微信目前机审大部分会从代码......
  • SSO单点登录基本概念实现思路以及小的实例详解
    一、什么是单点登录SSO(SingleSign-On)SSO是一种统一认证和授权机制,指访问同一服务器不同应用中的受保护资源的同一用户,只需要登录一次,即通过一个应用中的安全验证后,再访问其他应用中的受保护资源时,不再需要重新登录验证。二、单点登录解决了什么问题解决了用户只需要登录一......
  • 使用Java实现基于OAuth 2.0的单点登录功能
    本文将介绍如何使用Java编写一个基于OAuth2.0的单点登录系统,通过OAuth2.0实现用户在多个应用程序间的无缝登录体验1.什么是OAuth2.0?OAuth2.0是一种开放的授权框架,用于在应用程序之间安全地共享用户的身份验证和授权信息。它允许用户授权第三方应用程序代表其访问受保护的资......
  • mac安装php单点调试环境
    页面预览和抓包方式sudophp-fpmsudokillallphp-fpm开启/usr/local/etc/nginx/nginxnginx-squit运行Charles就行 单点调试环境方式:配置apache运行的目录,然后+phpStorm的xdebug就行,postman发请求带xdebug生成的keysudoapachectlstart浏览器debug打开,phpStorm配......
  • 基于Sa-Token实现微服务之前的单点登录
    修改配置文件,准备好四个域名127.0.0.1auth.server.com127.0.0.1user.server.com127.0.0.1third.server.com127.0.0.1eureka.server.com注册中心:eureka-server服务pom依赖<dependency><groupId>org.springframework.cloud</groupId>......
  • 微信小游戏代码包侵权解决办法
    微信过审机制介绍1、大致步骤就是提审->机器审核->人工审核;2、机器审核部分:审核代码部分,资源相关部分人工审核部分:审核UI相关,标题是否侵权,玩法是否符合类别3、审核时间:正常的账号在100分的情况下审核时间都会在2个小时内。审核细节1、微信目前机审大部分会从代码包里......
  • CAS SSO单点登录基础实践,配置CAS 服务器和CAS客户端
    参考网址:http://www.ibm.com/developerworks/cn/opensource/os-cn-cas/index.html 到CAS官方网站下载CASServer和Client,地址分别为:http://www.ja-sig.org/downloads/cas/cas-server-3.1.1-release.ziphttp://www.ja-sig.org/downloads/cas-clients/cas-client-java-3.0.0.z......
  • 树状数组详解!(C++_单点/区间查询_单点/区间修改)
    先把这张著名的树状数组结构图摆在最前面,接下来我们就以这张图讲起!       首先图中的A数组就是所谓的原数组,也就是普通的数组形态,C则是我们今天要说的树状数组(可以看出一个树的形状,但其实和树没多大关系)从图中可以明显看到以下几个式子:有点像前缀和不是?但这样还看不出什......