OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 6447|回复: 6

原子触摸屏实验计算问题

[复制链接]

44

主题

105

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
301
金钱
301
注册时间
2012-9-28
在线时间
0 小时
发表于 2013-1-11 12:18:37 | 显示全部楼层 |阅读模式

                                               
问题一:

            触摸屏校准参数 float xfac; float yfac; short xoff; short yoff; 这四个参数都是什么意思 具体点
还有

Pen_Point.xfac=(float)200/(pos_temp[1][0]-pos_temp[0][0]);//得到xfac
Pen_Point.xoff=(240-Pen_Point.xfac*(pos_temp[1][0]+pos_temp[0][0]))/2;//得到xoff

Pen_Point.yfac=(float)280/(pos_temp[2][1]-pos_temp[0][1]);//得到yfac
Pen_Point.yoff=(320-Pen_Point.yfac*(pos_temp[2][1]+pos_temp[0][1]))/2;//得到yoff

这几个公式怎么来的,主要是其中的数字 比如200 和240
                                        


 

问题二:

//外部中断初始化函数
void Touch_Init(void)
{           
 //注意,时钟使能之后,对GPIO的操作才有效
 //所以上拉之前,必须使能时钟.才能实现真正的上拉输出
 RCC->APB2ENR|=1<<4;    //PC时钟使能   
 RCC->APB2ENR|=1<<0;    //开启辅助时钟        
 GPIOC->CRL&=0XFFFF0000;//PC0~3
 GPIOC->CRL|=0X00003883;
 GPIOC->CRH&=0XFF0FFFFF;//PC13
 GPIOC->CRH|=0X00300000;//PC13推挽输出
 GPIOC->ODR|=0X200f;    //PC0~3 13 全部上拉   
  Read_ADS(&en_Point.X,&en_Point.Y);//第一次读取初始化   
 MY_NVIC_Init(2,0,EXTI1_IRQChannel,2); 
 RCC->APB2ENR|=0x01;    //使能io复用时钟    
    AFIO->EXTICR[0]|=0X0020; //EXTI13 映射到PC1  
 EXTI->IMR|=1<<1;        //开启line1上的中断
 EXTI->EMR|=1<<1;        //不屏蔽line1上的事件
 EXTI->FTSR|=1<<1;       //line1上事件下降沿触发 

......

....... 
            

上面红色部分什么意思?为什么是EXTI13 13??? 

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165540
金钱
165540
注册时间
2010-12-1
在线时间
2117 小时
发表于 2013-1-11 15:24:20 | 显示全部楼层
回复 支持 反对

使用道具 举报

10

主题

86

帖子

2

精华

中级会员

Rank: 3Rank: 3

积分
494
金钱
494
注册时间
2012-2-11
在线时间
9 小时
发表于 2013-1-11 15:32:52 | 显示全部楼层
回复【楼主位】kodianbao:
---------------------------------
呵呵!你可能没看原子哥的《不完全手册》和《STM32参考手册》。我这两天也在搞触屏,希望互相学习~~

问题一
看《不完全手册》PDF 的285页,看看原子哥写的实现原理,
如果还是不明白,就到论坛搜索关键字“触屏”或者到百度搜索“ 触屏校准原理”;
其中200我的理解是要求比例系数,这200为P1(20,20)P2(220,300)   则水平距离为220-20=200
240是因为屏幕为240*320的屏幕;

问题二
看《STM32参考手册》.PDF    126-127页的 外部中断配置寄存器1你就明白了;
多努力一点点,少遗憾一点点!!!
回复 支持 反对

使用道具 举报

44

主题

105

帖子

0

精华

中级会员

Rank: 3Rank: 3

积分
301
金钱
301
注册时间
2012-9-28
在线时间
0 小时
 楼主| 发表于 2013-1-11 22:35:15 | 显示全部楼层
回复【3楼】JZHG1992:
---------------------------------
谢谢
回复 支持 反对

使用道具 举报

15

主题

87

帖子

0

精华

初级会员

Rank: 2

积分
167
金钱
167
注册时间
2013-3-5
在线时间
0 小时
发表于 2013-4-22 21:55:46 | 显示全部楼层
回复【3楼】JZHG1992:
---------------------------------
那这句Pen_Point.yfac=(float)280/(pos_temp[2][1]-pos_temp[0][1]);//得到yfac,为什么会得到yfac,我感觉应该(float)280/(pos_temp[0][1]-pos_temp[0][0])这样?不知对不对
回复 支持 反对

使用道具 举报

10

主题

86

帖子

2

精华

中级会员

Rank: 3Rank: 3

积分
494
金钱
494
注册时间
2012-2-11
在线时间
9 小时
发表于 2013-4-23 08:28:52 | 显示全部楼层
回复【5楼】双星伴月:
---------------------------------


先看程序:


/***********************************************************
* 函数名称:Touch_Adjust
* 函数功能:触摸屏校准代码( 得到四个校准参数 )
*           入口参数:无      出口参数:0/1
***********************************************************/

void Touch_Adjust(void)
{  
signed short pos_temp[4][2];//坐标缓存值
u8  cnt=0;
u16 d1,d2;
u32 tem1,tem2;
float fac;     
cnt=0;
LCD_Clear(WHITE);//清屏    
Drow_Touch_Point(20,20,RED);//画点1 
Pen_Point.Key_Sta=Key_Up;//消除触发信号 
Pen_Point.xfac=0;//xfac用来标记是否校准过,所以校准之前必须清掉!以免错误  
while(1)
{
if(Pen_Point.Key_Sta==Key_Down)//按键按下了
{
if(TOUCH_ReadTPOnce())//得到单次按键值
{      
pos_temp[cnt][0]=Pen_Point.X;
pos_temp[cnt][1]=Pen_Point.Y;
cnt++;
}  
switch(cnt)
{    
case 1:
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(220,20,RED);//画点2
break;
case 2:
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(20,300,RED);//画点3
break;
case 3:
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(220,300,RED);//画点4
break;
case 4:  //全部四个点已经得到
         //对边相等
tem1=abs(pos_temp[0][0]-pos_temp[1][0]);//x1-x2
tem2=abs(pos_temp[0][1]-pos_temp[1][1]);//y1-y2
tem1*=tem1;
tem2*=tem2;
d1=sqrt(tem1+tem2);//开平方得到1,2的距离 

tem1=abs(pos_temp[2][0]-pos_temp[3][0]);//x3-x4
tem2=abs(pos_temp[2][1]-pos_temp[3][1]);//y3-y4
tem1*=tem1;
tem2*=tem2;
d2=sqrt(tem1+tem2);//得到3,4的距离
fac=(float)d1/d2; 
if(fac<0.95||fac>1.05||d1==0||d2==0)//不合格
{
cnt=0;
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(20,20,RED);
ADJ_INFO_SHOW("ver fac is:",RED);   
LCD_ShowNum(40+24,40,pos_temp[0][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,40,pos_temp[0][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,60,pos_temp[1][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,60,pos_temp[1][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,80,pos_temp[2][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,80,pos_temp[2][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,100,pos_temp[3][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,100,pos_temp[3][1],4,0,RED); //显示数值
//扩大100倍显示
LCD_ShowNum(40,140,fac*100,3,0,RED);//显示数值,该数值必须在95~105范围之内.
continue;
}
tem1=abs(pos_temp[0][0]-pos_temp[2][0]);//x1-x3
tem2=abs(pos_temp[0][1]-pos_temp[2][1]);//y1-y3
tem1*=tem1;
tem2*=tem2;
d1=sqrt(tem1+tem2);//得到1,3的距离

tem1=abs(pos_temp[1][0]-pos_temp[3][0]);//x2-x4
tem2=abs(pos_temp[1][1]-pos_temp[3][1]);//y2-y4
tem1*=tem1;
tem2*=tem2;
d2=sqrt(tem1+tem2);//得到2,4的距离
fac=(float)d1/d2;
if(fac<0.95||fac>1.05)//不合格
{
cnt=0;
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(20,20,RED);
ADJ_INFO_SHOW("hor fac is:",RED);   
LCD_ShowNum(40+24,40,pos_temp[0][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,40,pos_temp[0][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,60,pos_temp[1][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,60,pos_temp[1][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,80,pos_temp[2][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,80,pos_temp[2][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,100,pos_temp[3][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,100,pos_temp[3][1],4,0,RED); //显示数值
//扩大100倍显示
LCD_ShowNum(40,140,fac*100,3,0,RED);//显示数值,该数值必须在95~105范围之内.
  continue;
}//正确了
   
//对角线相等
tem1=abs(pos_temp[1][0]-pos_temp[2][0]);//x1-x3
tem2=abs(pos_temp[1][1]-pos_temp[2][1]);//y1-y3
tem1*=tem1;
tem2*=tem2;
d1=sqrt(tem1+tem2);//得到1,4的距离

tem1=abs(pos_temp[0][0]-pos_temp[3][0]);//x2-x4
tem2=abs(pos_temp[0][1]-pos_temp[3][1]);//y2-y4
tem1*=tem1;
tem2*=tem2;
d2=sqrt(tem1+tem2);//得到2,3的距离
fac=(float)d1/d2;
if(fac<0.95||fac>1.05)//不合格
{
cnt=0;
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(20,20,RED);
ADJ_INFO_SHOW("dia fac is:",RED);   
LCD_ShowNum(40+24,40,pos_temp[0][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,40,pos_temp[0][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,60,pos_temp[1][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,60,pos_temp[1][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,80,pos_temp[2][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,80,pos_temp[2][1],4,0,RED); //显示数值
LCD_ShowNum(40+24,100,pos_temp[3][0],4,0,RED); //显示数值
LCD_ShowNum(40+24+80,100,pos_temp[3][1],4,0,RED); //显示数值
//扩大100倍显示
LCD_ShowNum(40,140,fac*100,3,0,RED);//显示数值,该数值必须在95~105范围之内.
continue;
}//正确了
//计算结果
Pen_Point.xfac=(float)200/(pos_temp[1][0]-pos_temp[0][0]);//得到xfac  
Pen_Point.xoff=(240-Pen_Point.xfac*(pos_temp[1][0]+pos_temp[0][0]))/2;//得到xoff
  
Pen_Point.yfac=(float)280/(pos_temp[2][1]-pos_temp[0][1]);//得到yfac
Pen_Point.yoff=(320-Pen_Point.yfac*(pos_temp[2][1]+pos_temp[0][1]))/2;//得到yoff  

if(abs(Pen_Point.xfac)>2||abs(Pen_Point.yfac)>2)//触屏和预设的相反了.
{
cnt=0;
LCD_Clear(WHITE);//清屏 
Drow_Touch_Point(20,20,RED);
LCD_ShowString(35,110,"TP Need readjust!",0,RED);
Pen_Point.touchtype=!Pen_Point.touchtype;//修改触屏类型.
if(Pen_Point.touchtype)//X,Y方向与屏幕相反
{
CMD_RDX=0X90;
CMD_RDY=0XD0;  
}else    //X,Y方向与屏幕相同
{
CMD_RDX=0XD0;
CMD_RDY=0X90;  
}
Delay_nms(500);
continue;
}
LCD_Clear(WHITE);//清屏
LCD_ShowString(35,110,"Touch Screen Adjust OK!",1,BLUE);//校正完成
Delay_nms(500);
LCD_Clear(WHITE);//清屏   
return;//校正完成  
}
}

}     


我的理解是:
假设得到屏幕四个点         1(x1,y1)、P2(x2,y1)
         P3(x1,y2)、P4(x2,y2)

 而pos_temp[0][0]=x1,     pos_temp[0][1]=y1,    
    pos_temp[1][0]=x2,     pos_temp[1][1]=y1,   
    pos_temp[2][0]=x1,     pos_temp[2][1]=y2, 
    pos_temp[3][0]=x2,     pos_temp[3][1]=y2, 

原子哥取值为左上角的坐标是一组非0的数值,比如(20,20),而右下角的坐标为(220,300)

所以Y轴比例因子 yfac=(float)(300-20)/(y2-y1)= (float)(280)/(pos_temp[2][1]-pos_temp[0][1]) 

或者yfac=(float)(280)/(pos_temp[3][1]-pos_temp[1][1]) 

而你的(float)280/(pos_temp[0][1]-pos_temp[0][0])  ==》 (float)280/(y1-x1);   

所以我认为可能不行,以上是我个人理解~~
多努力一点点,少遗憾一点点!!!
回复 支持 反对

使用道具 举报

15

主题

87

帖子

0

精华

初级会员

Rank: 2

积分
167
金钱
167
注册时间
2013-3-5
在线时间
0 小时
发表于 2013-4-23 13:23:22 | 显示全部楼层
回复【6楼】JZHG1992:
---------------------------------
嗯,后来也发现了。把那四个坐标画出来看就理解那个了。谢谢了哈
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-7-21 05:33

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表