linux的触摸屏之四:android的tslib对下层Linux的控制

(1)三星的触摸屏驱动s3c-ts.c:

s3c_ts_init-》platform_driver_register(&s3c_ts_driver);

static struct platform_driver s3c_ts_driver = {
       .probe          = s3c_ts_probe,
       .driver  = {
  .owner = THIS_MODULE,
  .name = "s3c-ts",},
};

通过"s3c-ts"字符串与dev-ts.c的s3c_device_ts中的name字串匹配,实现注册。

static int __init s3c_ts_probe(struct platform_device *pdev)

{

      platform_get_resource(pdev, IORESOURCE_MEM, 0);   //获得MEM资源

      request_mem_region(res->start, size, pdev->name);   //获得MEM资源大小

      ioremap(res->start, size);        //对MEM资源重新IO

      clk_enable(ts_clock);                //TS的CLK使能

      struct s3c_ts_mach_info *s3c_ts_cfg = s3c_ts_get_platdata(&pdev->dev);    //获得默认的ts配置数据,如采样率,通道

      struct input_dev *input_dev = input_allocate_device();

 

      ts->dev->name = s3c_ts_name;
      ts->dev->phys = ts->phys;
      ts->dev->id.bustype = BUS_RS232;
      ts->dev->id.vendor = 0xDEAD;
      ts->dev->id.product = 0xBEEF;
      ts->dev->id.version = S3C_TSVERSION;         //完善ts的input_dev参数

 

      ts_irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);

      request_irq(ts_irq->start, stylus_updown, IRQF_SAMPLE_RANDOM, "s3c_updown", ts);  //触点中断

      ts_irq = platform_get_resource(pdev, IORESOURCE_IRQ, 1);、

      request_irq(ts_irq->start, stylus_action, IRQF_SAMPLE_RANDOM, "s3c_action", ts);  //ADC中断操作

 

      input_register_device(ts->dev);    //注册输入设备到input层

      ret = misc_register(&s3c_ts_miscdev);  //注册字符设备,方便上层调用

}

(2)注册字符设备的作用。

struct file_operations s3c_ts_fops = {
     .owner  = THIS_MODULE,
     .read  = s3c_ts_read,
     .write    = s3c_ts_write,
     .open  = s3c_ts_open,
     .release    = s3c_ts_release,
};

#define S3C_TS_MINOR  222
static struct miscdevice s3c_ts_miscdev = {
     .minor  = S3C_TS_MINOR,
     .name  = "myts",
     .fops  = &s3c_ts_fops,
};

为方便上层调用。比如cupcake层的:

 char buffer[5] = "OK";
 int fd = open("/dev/myts",O_RDWR);
 printf("fd: %d/n",fd);
 write(fd,buffer,2); 
 close(fd);

这里的write函数将会直接调用字符设备驱动中的write函数指针,把数据从用户空间传递到内核空间。

static ssize_t  s3c_ts_write(struct file *file, const char __user * buffer,  size_t size, loff_t * pos)
{
     char from_user_to[5];

     if (copy_from_user(from_user_to, buffer, 2))//buffer: "OK" or "END"
     {
           return -EFAULT;
     }
     if(from_user_to[0]=='O'&&from_user_to[1]=='K')//if  =="OK",need calibrate;     //OK
     {
           start_calibrate_flag  = 1;
           finish_calibrate_flag = 0;
     }
     else if(from_user_to[0]=='E'&&from_user_to[1]=='N')//calibrate is over            //END
     {

            start_calibrate_flag = 0;
            finish_calibrate_flag = 1;
     }
     else
     {
            start_calibrate_flag = 0;
            finish_calibrate_flag =0;
      }
      return 0;
}
(3)触摸屏中断的处理。有两个中断,一个是TS按下跟弹起的中断stylus_updown,另一个是ADC的中断stylus_action。这两个函数都会用到touch_timer_fire这个函数。

static int read_one_time = 0;   //标记只控制一次

static void touch_timer_fire(unsigned long data)

{

      updown = (!(data0 & S3C_ADCDAT0_UPDOWN)) && (!(data1 & S3C_ADCDAT1_UPDOWN));

      if (updown)    //处于按下状态

     {

             if(!read_one_time)//read calibrate parameter only once after power on
             {

                     read_one_time = 1;  //用完后置1,表示该部分就执行一次

                     a0 = default_val[0];a1 = default_val[1];a2 = default_val[2];a3 = default_val[3];
                     a4 = default_val[4];a5 = default_val[5];a6 = default_val[6];   //对七个参数赋初始默认值

                     if(read_file("/system/etc/pointercal")==0)
                     {
                            a0 = calpointer[0];a1 = calpointer[1];a2 = calpointer[2];a3 = calpointer[3];
                            a4 = calpointer[4];a5 = calpointer[5];a6 = calpointer[6];
                      }  //读出系统中经tslib校验后放在pointercal中的七个参数,作为真正要用的值

                      calpointer[0] =0;calpointer[1] =0;calpointer[2] =0;calpointer[3] =0;
                      calpointer[4] =0;calpointer[5] =0;calpointer[6] =0;   //用完后清零

              }

              x=(int) ts->xp;y=(int) ts->yp;    //得到之前的ts->xp和ts->yp

              if(!start_calibrate_flag)             //如果不是重新开始校验,那么接着上面根据公式和新参数计算新坐标值
              {
                      ts->xp=(long) ((a2+(a0*x)+(a1*y))/a6);
                      ts->yp=(long) ((a5+(a3*x)+(a4*y))/a6); 
                      ts->xp = ts->xp < 0 ? 0:( ts->xp > PANEL_WIDTH ? PANEL_WIDTH : ts->xp );
                      ts->yp = ts->yp < 0 ? 0:( ts->yp > PANEL_HEIGHT ? PANEL_HEIGHT : ts->yp );
              }

              else  //如果是运行校验程序重新校验的

              {

                     if(finish_calibrate_flag)   //而且校验完毕了
                    {
                           start_calibrate_flag = 0;finish_calibrate_flag = 0;   //清标志
                           if(read_file("/system/etc/pointercal")==0)
                           {
                                  a0 = calpointer[0];a1 = calpointer[1];a2 = calpointer[2];a3 = calpointer[3];
                                  a4 = calpointer[4];a5 = calpointer[5];a6 = calpointer[6];
                                  calpointer[0] =0;calpointer[1] =0;calpointer[2] =0;calpointer[3] =0;
                                  calpointer[4] =0;calpointer[5] =0;calpointer[6] =0;   //获得新参数及清空
                            } 

                      }

               }

               if(ts->xp!=ts->xp_old || ts->yp!=ts->yp_old)   //如果坐标值有变更
              {
                      input_report_abs(ts->dev, ABS_X, ts->xp);
                      input_report_abs(ts->dev, ABS_Y, ts->yp);
                      input_report_abs(ts->dev, ABS_Z, 0);

                      input_report_key(ts->dev, BTN_TOUCH, 1);
                      input_report_abs(ts->dev, ABS_PRESSURE, 1);
                      input_sync(ts->dev);        //将新的坐标值传递给Input层,及android上层
              }
              ts->xp_old=ts->xp;
              ts->yp_old=ts->yp;    //保留新值

     }

     else                 //处于弹起状态

     {

             input_report_abs(ts->dev, ABS_X, ts->xp_old);
             input_report_abs(ts->dev, ABS_Y, ts->yp_old);
             input_report_abs(ts->dev, ABS_Z, 0);                 //传递绝对坐标值给input层

             input_report_key(ts->dev, BTN_TOUCH, 0);        //触摸事件

             input_report_abs(ts->dev, ABS_PRESSURE, 0);  //触摸压力为0,弹起

             input_sync(ts->dev);                                           //将input report数据同步更新

     }

}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
引用:D:\Linux-4.9.88.tar\Linux-4.9.88\include\uapi\linux input.h 。 引用:cp -d lib/*so* /home/book/100ask_imx6ull-sdk/ToolChain/gcc-linaro-6.2.1-2016.11-x86_64_arm-linux-gnueabihf/bin/../arm-linux-gnueabihf/libc/usr/lib/ (2)板子上测试编译 。 引用:1,上网搞个源码库,如果你可爱到不会用百度,没关系,戳我下载( http://download.csdn.net/detail/vincent040/9662825 )。 2,将源代码丢到Ubuntu,并通过以下命令解压到Ubuntu的家目录下: tar xjvf tslib-1.4.tar.bz2 -C ~ 3,进入源码顶层目录,依次执行如下命令: mkdir ~/tslib ./configure --prefix=/home/xxx/tslib --host=arm-none-linux-gnueabi make make install A) --prefix= 后面的路径就是你要安装 tslib 库的路径,墙裂建议设置为家目录下的空目录(比如~/tslib),因为如果设置系统其它目录的话,后期 make install 的时候会让你解决权限的问题,当你自作聪明地使用sudo的时候,系统却又可能会抱怨找不到工具链,因此除非你是 Ubuntu科学家,对系统环境变量了如指掌,否则不要用小白的身份去作死,乖乖将 --prefix 指定为 ~/tslib 即可。 根据提供的引用内容,可以看出tslib是一个Linux上的触摸屏输入子系统库。它提供了在嵌入式系统中处理触摸屏输入的功能和接口。要安装tslib库,可以按照以下步骤进行操作:首先,下载源码库并将源代码解压到Ubuntu的家目录下;接着进入源码顶层目录,创建一个空目录(比如~/tslib)作为安装路径,并执行configure命令来配置安装参数;然后使用make命令编译源代码;最后使用make install命令安装tslib库到指定的安装路径。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值