彻底解决2440/2410触摸屏跳点以及抖动问题
来源:互联网 发布:北微传感器 淘宝 编辑:程序博客网 时间:2024/03/29 16:16
一位CSDN牛人的详尽触摸屏校正方法
多个LCD下修改DISPLAY与TOUCHP驱动的经验
首先说明,我所做的是基于s3c2410的wince平台。
更换LCD之后一般需要修改DISPLAY与TOUCHP驱动。建议大家把公共一些宏提取出来,独立写个头文件使用。需要参考的文件除了2个驱动对应的c/cpp文件还有s2410.h。cfw.c里面也有关于LCD的问题。如果你有对他做了修改,那么自己需要注意了。我之前自己的包就是。
我提取的部分信息:
... ... ...
#define LCD_TYPE TFT640_480
#if ( LCD_TYPE == TFT640_480 )
#define SRC_WIDTH (640)
#define SRC_HEIGHT (480)
#define MemSize (0xA0000)
#define LCD_XSIZE_TFT (SRC_WIDTH)
#define LCD_YSIZE_TFT (SRC_HEIGHT)
//触摸区域修改下面的值
#define TOUCH_MAX_X 1080
#define TOUCH_MIN_X 10
#define TOUCH_MAX_Y 980
#define TOUCH_MIN_Y 30
#define TOUCH_X SRC_WIDTH
#define TOUCH_Y SRC_HEIGHT
//屏幕显示时隙设置 参考LCD厂商给出的资料
#define VBPD ((20) & 0xff)
#define VFPD ((2) & 0xff)
#define VSPW ((1) & 0x3f)
#define HBPD ((121) & 0x7f)
#define HFPD ((15) & 0xff)
#define HSPW ((13) & 0xff)
//#define ADC_DELAY_TIME 5000 看你具体情况我独立放开来,因为有好几种液晶。
#elif (...)
... ... ...
#endif
... ... ...
以后不管什么LCD需要处理,直接修改LCD_TYPE就行了。如果你跟我一样,同种大小也有几种不同厂商提供的LCD,那么你还需要定义一个宏来区分厂商的,写好以后需要换就修改1-2个宏的值就可以了,同时提取出来的宏再原来的文件中记得注释掉,免得重定义。不要去覆盖好几个地方。当然这样或许不完美,还存在触摸需要校正的问题。下面再说说我的做法。
1.首先拿到LCD,烧完让他跑起来。
2.用wince自带的校正程序校正。然后用PB或者EVC的工具连接wince的注册表。找到下面对应的值。
[HKEY_LOCAL_MACHINE/HARDWARE/DEVICEMAP/TOUCH]
"CalibrationData"="这里每人的值都不一样"
在$(_FLATRELEASEDIR)目录下的platform.reg里面找到“[HKEY_LOCAL_MACHINE/HARDWARE/DEVICEMAP/TOUCH]”
修改"CalibrationData"的值为找到的。然后make一下。重新写进去测试。
这个时候特别需要测试的是屏蔽的边缘的触摸效果,如果正常,那么恭喜你,可以了。如果边缘有问题,进行下一步3。
3.修改触摸区域。
#define TOUCH_MAX_X
#define TOUCH_MIN_X
#define TOUCH_MAX_Y
#define TOUCH_MIN_Y
调整这个区域(一般我见到的情况是边缘没反映或者点击后效果靠中心,所以把区域放到就行)。然后转1再进行测试。(个人出现过边缘无反应后解决,故与将校准放一起)
一般几步就OK了。
最后记得把CalibrationData的值保存起来放到platform.reg里面,以后如果更换LCD,那么直接修改platform.reg文件,把对应的值放出来,其他的注释调编译一下就可以了。根本不需要再校正。
以上转自:http://blog.csdn.net/gooogleman/article/details/3191875
// Topic:彻底解决2440触摸屏跳点问题
//作者:gooogleman
//版权:桂林电子科技大学一系科协wogoyixikexie@gliet.gooogleman
//平台:wince5.0 2440 5.0 BSP(飞凌FL2440开发板)
//发布日期:2010年11月18日
//最后修改:
//技术论坛:www.gooogleman.com
//注意事项:商业网站未经作者同意不能转载,并且不能删除文章的任何部分,否则追究责任!
//-------------------------------------------------------------------------------------------------
其实2440触摸屏跳点问题在前一个多月已经得到解决,在我解决6410 触摸屏抖动的时候,偶然发现6410 不会任何跳点,只是抖动,后来比较2440 和6410 的触摸屏驱动写法,发现6410的比较惊异,算法避免了天外飞仙跳点。
ooo,下班了,明天再写吧。
——续@2010-11-19
我仔细比较6410 触摸屏驱动和2440 驱动,发现6410 的写法比较合理一些,最大区别是DdsiTouchPanelGetPoint函数写法,下面是2440 会跳点的写法。
从上面可以看出,这个DdsiTouchPanelGetPoint里面只进行了一步采样,尽管采样次数大于1次,但是也绝对不能消除天外飞仙跳点。因为这几次采样时间太靠近了,所以采样值都会很相近,即使是多次采样(我曾经试过20 次,没有多大改善。),求平均值,效果也会很微小。这个情况就说明,要想触摸屏不跳点,就要消除错误的采样点,那么怎么做呢?上面每隔10ms 连续采样多次无效,原因是每次采样间隔时间太短,数据太密集,接近,导致仍然获得的是误差数据。假设想想,如果扩大采样时间间隔去采样,这样获得的数据就不会太接近就可以判断了吧?看看6410 的触摸屏驱动,果然是每隔10ms 采样两组数据的,并且这两组数据进行比较分析,误差过大就说明采样点是无效的,这样就把天外飞仙的现象去掉了。下面也贴出改好的2440 代码,希望大家有帮助。
001
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
002
003
004
005
PUBLIC
VOID
006
DdsiTouchPanelGetPoint(TOUCH_PANEL_SAMPLE_FLAGS * pTipStateFlags,
007
INT
* pUncalX,
008
INT
* pUncalY)
009
{
010
static
INT
x, y;
011
int
TmpX = 0;
012
int
TmpY = 0;
013
014
if
(v_pINTregs->SUBSRCPND & (1<<IRQ_SUB_TC))
/* SYSINTR_TOUCH Interrupt Case*/
015
{
016
*pTipStateFlags = TouchSampleValidFlag;
017
018
if
( (v_pADCregs->ADCDAT0 & (1 << 15)) |
019
(v_pADCregs->ADCDAT1 & (1 << 15)) )
020
{
021
bTSP_DownFlag = FALSE;
022
023
DEBUGMSG(ZONE_TIPSTATE, (TEXT(
"up/r/n"
)));
024
025
v_pADCregs->ADCTSC &= 0xff;
026
027
*pUncalX = x;
028
*pUncalY = y;
029
030
TSP_SampleStop();
031
// Test
032
033
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = FALSE...PenUP!!!/r/n"
)));
034
}
035
else
036
{
037
bTSP_DownFlag = TRUE;
038
039
//if (!TSP_GetXY(&x, &y))
040
// *pTipStateFlags = TouchSampleIgnore;
041
042
//TSP_TransXY(&x, &y);
043
044
//-----------------------add @2010.09.11-----------------------
045
*pTipStateFlags |= TouchSampleIgnore;
046
047
*pUncalX = x;
048
*pUncalY = y;
049
050
*pTipStateFlags |= TouchSampleDownFlag;
051
052
//Test
053
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = TRUE...PenDown!!!/r/n"
)));
054
055
TSP_SampleStart();
056
}
057
058
v_pINTregs->SUBSRCPND = (1<<IRQ_SUB_TC);
059
v_pINTregs->INTSUBMSK &= ~(1<<IRQ_SUB_TC);
060
061
InterruptDone(gIntrTouch);
062
}
063
else
/* SYSINTR_TOUCH_CHANGED Interrupt Case */
064
{
065
// TSP_SampleStart();
066
067
if
(bTSP_DownFlag)
068
{
069
if
(TSP_GetXY(&TmpX, &TmpY) == TRUE)
070
{
071
//TSP_TransXY(&TmpX, &TmpY);
072
073
if
(Touch_Pen_Filtering(&TmpX, &TmpY))
074
{
075
*pTipStateFlags = TouchSampleValidFlag | TouchSampleDownFlag;
076
*pTipStateFlags &= ~TouchSampleIgnore;
077
}
078
else
// Invalid touch pen
079
{
080
*pTipStateFlags = TouchSampleValidFlag;
081
*pTipStateFlags |= TouchSampleIgnore;
082
}
083
084
*pUncalX = x = TmpX;
085
*pUncalY = y = TmpY;
086
}
087
else
088
{
089
*pTipStateFlags = TouchSampleIgnore;
090
}
091
}
092
else
093
{
094
*pTipStateFlags = TouchSampleIgnore;
095
096
TSP_SampleStop();
097
098
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = FALSE.PenDown!!!IRQ_Timer3 Interrupt/r/n"
)));
099
}
100
101
InterruptDone(gIntrTouchChanged);
102
}
103
104
// add by wogo at2009.03.23 why?
105
SetEvent(hEventTouchInput);
106
}
107
108
109
110
static
BOOL
111
Touch_Pen_Filtering(
INT
*px,
INT
*py)
112
{
113
BOOL
RetVal = TRUE;
114
// TRUE : Valid pen sample
115
// FALSE : Invalid pen sample
116
INT
Filter_Margin;
117
static
int
count = 0;
118
static
INT
x[2], y[2];
119
INT
TmpX, TmpY;
120
INT
dx, dy;
121
122
if
(*px <0 && *py <0)
123
{
124
count = 0;
125
return
FALSE;
126
}
127
else
128
{
129
count++;
130
}
131
132
if
(count > 2)
133
{
134
// apply filtering rule
135
count = 2;
136
137
// average between x,y[0] and *px,y
138
TmpX = (x[0] + *px)>>1;
139
TmpY = (y[0] + *py)>>1;
140
141
// difference between x,y[1] and TmpX,Y
142
dx = (x[1] > TmpX) ? (x[1] - TmpX) : (TmpX - x[1]);
143
dy = (y[1] > TmpY) ? (y[1] - TmpY) : (TmpY - y[1]);
144
145
Filter_Margin = (x[1] > x[0]) ? (x[1]-x[0]) : (x[0]-x[1]);
146
Filter_Margin += (y[1] > y[0]) ? (y[1]-y[0]) : (y[0]-y[1]);
147
Filter_Margin += TSP_FILTER_LIMIT;
148
149
if
((dx > Filter_Margin) || (dy > Filter_Margin)) {
150
// Invalid pen sample
151
*px = x[1];
152
*py = y[1];
// previous valid sample
153
RetVal = FALSE;
154
count = 0;
155
}
156
else
157
{
158
// Valid pen sample
159
x[0] = x[1]; y[0] = y[1];
160
x[1] = *px; y[1] = *py;
// reserve pen samples
161
162
RetVal = TRUE;
163
}
164
}
165
else
// (count > 2)
166
{
// till 2 samples, no filtering rule
167
x[0] = x[1]; y[0] = y[1];
168
x[1] = *px; y[1] = *py;
// reserve pen samples
169
170
RetVal = FALSE;
// <- TRUE jylee 2003.03.04
171
}
172
173
return
RetVal;
174
175
}
现在测试2440 的触摸屏,我们会惊奇的发现,真的没有天外飞仙跳点了,不过又引入了一个新的问题,触摸屏抖动!以前的那种写法采样时间间隔短,数据集中,是不会抖动的,现在数据差异大,触摸屏抖动的相当的厉害了!怎么办呢?这个时候增大采样次数求平均值会有一些效果,不过还是不能完全消除抖动的!现在就要用一个简单的算法了:就是采样八个点,然后从小到大排序之后,把最大和最小值去掉,因为这两个值通常都是在受力不均的时候产生的,不是真实的值,所以丢了,再求剩余几个点的平均值,这样就可以完美的消除触摸屏抖动了,下面贴出代码,希望大家也来改进一下。
01
PRIVATE
BOOL
02
TSP_GetXY(
INT
*px,
INT
*py)
03
{
04
int
i,j,k,temp;
05
//INT xsum, ysum;
06
//int x, y;
07
int
dx, dy;
08
int
x[TSP_SAMPLE_NUM], y[TSP_SAMPLE_NUM];
09
10
//xsum = ysum = 0;
11
EnterCriticalSection(&g_csTouchADC);
12
for
(i = 0; i < TSP_SAMPLE_NUM; i++)
13
{
14
v_pADCregs->ADCTSC = (0<<8)|(1<<7)|(1<<6)|(0<<5)|(1<<4)|(1<<3)|(1<<2)|(0);
15
v_pADCregs->ADCCON |= (1 << 0);
/* Start Auto conversion */
16
17
while
(v_pADCregs->ADCCON & 0x1);
/* check if Enable_start is low */
18
while
(!(v_pADCregs->ADCCON & (1 << 15)));
/* Check ECFLG */
19
20
x[i] = (0x3ff & v_pADCregs->ADCDAT1);
21
y[i] = 0x3ff - (0x3ff & v_pADCregs->ADCDAT0);
22
23
//x[i] = D_XPDATA_MASK(v_pADCregs->ADCDAT1);
24
//y[i] = D_YPDATA_MASK(v_pADCregs->ADCDAT0);
25
//xsum += x;
26
//ysum += y;
27
}
28
29
//*px = xsum / TSP_SAMPLE_NUM;
30
//*py = ysum / TSP_SAMPLE_NUM;
31
32
v_pADCregs->ADCTSC = (1<<8)|(1<<7)|(1<<6)|(0<<5)|(1<< 4)|(0<<3)|(0<<2)|(3);
33
34
35
LeaveCriticalSection(&g_csTouchADC);
36
37
//--------------------------------------------------------------
38
// if mask it ,very tremble work not well
39
for
(j = 0; j < TSP_SAMPLE_NUM -1; ++j)
40
{
41
for
(k = j+1; k < TSP_SAMPLE_NUM; ++k)
42
{
43
if
(x[j]>x[k])
44
{
45
temp = x[j];
46
x[j]=x[k];
47
x[k]=temp;
48
}
49
50
if
(y[j]>y[k])
51
{
52
temp = y[j];
53
y[j]=y[k];
54
y[k]=temp;
55
}
56
}
57
}
58
59
//dx = (*px > x) ? (*px - x) : (x - *px);
60
//dy = (*py > y) ? (*py - y) : (y - *py);
61
62
*px = (x[2] + ((x[3]+x[4])<<1) + (x[3]+x[4]) + x[5]);
63
*py = (y[2] + ((y[3]+y[4])<<1) + (y[3]+y[4]) + y[5]);
64
65
if
((*px & 0x7) > 3)
66
*px = (*px>>3) + 1;
67
else
*px = *px>>3;
68
69
if
((*py & 0x7) > 3)
70
*py = (*py>>3) + 1;
71
else
*py = *py>>3;
72
73
dx = x[5] - x[2];
74
dy = y[5] - y[2];
75
76
return
((dx > TSP_INVALIDLIMIT || dy > TSP_INVALIDLIMIT) ? FALSE : TRUE);
77
}
好了,方法就是这么多了,This is it ,下面贴出效果图,收工!
wince 2440 完美解决触摸屏跳点抖动源码
http://www.gooogleman.com/forum.php?mod=viewthread&tid=507&fromuid=3
001
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
002
/* :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: */
003
004
005
006
PUBLIC
VOID
007
DdsiTouchPanelGetPoint(TOUCH_PANEL_SAMPLE_FLAGS * pTipStateFlags,
008
INT
* pUncalX,
009
INT
* pUncalY)
010
{
011
static
INT
x, y;
012
013
if
(v_pINTregs->SUBSRCPND & (1<<IRQ_SUB_TC))
/* SYSINTR_TOUCH Interrupt Case*/
014
{
015
*pTipStateFlags = TouchSampleValidFlag;
016
017
if
( (v_pADCregs->ADCDAT0 & (1 << 15)) |
018
(v_pADCregs->ADCDAT1 & (1 << 15)) )
019
{
020
bTSP_DownFlag = FALSE;
021
022
DEBUGMSG(ZONE_TIPSTATE, (TEXT(
"up/r/n"
)));
023
024
v_pADCregs->ADCTSC &= 0xff;
025
026
*pUncalX = x;
027
*pUncalY = y;
028
029
TSP_SampleStop();
030
// Test
031
032
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = FALSE...PenUP!!!/r/n"
)));
033
}
034
else
035
{
036
bTSP_DownFlag = TRUE;
037
038
if
(!TSP_GetXY(&x, &y))
039
*pTipStateFlags = TouchSampleIgnore;
040
041
TSP_TransXY(&x, &y);
042
043
*pUncalX = x;
044
*pUncalY = y;
045
046
*pTipStateFlags |= TouchSampleDownFlag;
047
048
//Test
049
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = TRUE...PenDown!!!/r/n"
)));
050
051
TSP_SampleStart();
052
}
053
054
v_pINTregs->SUBSRCPND = (1<<IRQ_SUB_TC);
055
v_pINTregs->INTSUBMSK &= ~(1<<IRQ_SUB_TC);
056
057
InterruptDone(gIntrTouch);
058
}
059
else
/* SYSINTR_TOUCH_CHANGED Interrupt Case */
060
{
061
// TSP_SampleStart();
062
063
if
(bTSP_DownFlag)
064
{
065
INT
tx, ty;
066
INT
dx, dy;
067
068
if
(!TSP_GetXY(&tx, &ty))
069
*pTipStateFlags = TouchSampleIgnore;
070
else
071
{
072
073
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = TRUE.PenDown!!!IRQ_Timer3 Interrupt/r/n"
)));
074
TSP_TransXY(&tx, &ty);
075
// insert by mostek@dstcorp.com
076
#define X_ERRV 0x3bf
077
#define Y_ERRV 0x4ff
078
079
if
((tx == X_ERRV) && (ty == Y_ERRV))
080
{
081
tx = x;
082
ty = y;
083
}
084
// =================== mostek
085
dx = (tx > x) ? (tx - x) : (x - tx);
086
dy = (ty > y) ? (ty - y) : (y - ty);
087
088
if
(dx > TSP_CHANGE || dy > TSP_CHANGE)
089
{
090
*pUncalX = x = tx;
091
*pUncalY = y = ty;
092
093
//DEBUGMSG(ZONE_TIPSTATE, (TEXT("down-c-v %x %x/r/n"), x, y));
094
*pTipStateFlags = TouchSampleValidFlag | TouchSampleDownFlag;
095
}
096
else
097
{
098
*pUncalX = x;
099
*pUncalY = y;
100
101
DEBUGMSG(ZONE_TIPSTATE, (TEXT(
"down-c %x %x/r/n"
), x, y));
102
103
*pTipStateFlags = TouchSampleIgnore;
104
}
105
}
106
}
107
else
108
{
109
*pTipStateFlags = TouchSampleIgnore;
110
111
TSP_SampleStop();
112
113
RETAILMSG(1,(TEXT(
"bTSP_DownFlag = FALSE.PenDown!!!IRQ_Timer3 Interrupt/r/n"
)));
114
}
115
116
InterruptDone(gIntrTouchChanged);
117
}
118
119
// add by wogo at2009.03.23 why?
120
SetEvent(hEventTouchInput);
121
}
- 彻底解决2440/2410触摸屏跳点以及抖动问题
- 彻底解决2440触摸屏跳点以及抖动问题
- 彻底解决2440触摸屏跳点以及抖动问题
- S3C2440触摸屏消除跳点及抖动
- 如何解决触摸屏抖动问题
- 触摸屏跳点问题分析
- S3C2440/6410 TOUCH抖动问题彻底解决
- S3C2440/6410 TOUCH抖动问题彻底解决
- 防止窗口抖动以及窗体不刷新问题
- wince 电阻触摸屏去抖动新思路
- 处理触摸屏抖动的一些方法
- 彻底解决iOS7状态栏隐藏的问题(以及setStatusBarHidden:YES不起作用问题)
- shell以及几点问题
- 彻底解决APP渠道统计和邀请码之痛点问题
- Dom4j 编码问题彻底解决
- Dom4j 编码问题彻底解决
- Dom4j 编码问题彻底解决
- Ajax中文问题彻底解决
- ubuntu10.04下qtcreator和opencv安装配置
- 研究生如何写论文
- 在ubuntu10.04建立opencv交叉编译环境
- ubuntu10.04下安装使用opencv
- 安装xampp
- 彻底解决2440/2410触摸屏跳点以及抖动问题
- maverick组件实现JAVA SSH协议初探
- (gedit:1962): Gtk-WARNING **: Attempting to store changes into `/root/.local/share/recently-used.xbe
- 常用linux压缩解压命令tar
- FAQ_19 如何判断 android 版本
- 一个C程序员的个人开发经验,(三)变量定义
- 台达ASDA-B2和ECMA-E2伺服电子齿轮比的计算
- uboot移植之uboot和kernel的参数传递
- 声明