mini2440裸试验—计算器(LCD显示,触摸屏突破)
关于Pait_Bmp(x0,
y0, x,
y, BMPaddr);函数
像素图在屏幕左上角为(0,0),Pait_Bmp中的x0。y0分别像素点初始位置,x,y为BMP图片的X,Y的大小。BMPaddr为BMP图片转换的数组地址
基于T35 TFT LCD屏实现功能:
1. 在屏幕上画一个计算器界面,包含0-9,+。-,*。/;
2. 实现触摸选择界面上的数字和运算符。
3. 并计算出结果显示在显示框内。
注意。仅仅实现整数功能,没涉及小数。仅仅实现一次运算,不保存上次运算结果。
实现界面:
实现过程:
开启LCD电源,初始化LCD>>>LCD填充界面图片>>>开启触摸屏中断>>>获取键值>>>区分数字和功能来调用数字图片显示。
数字图片:
空白图: 除数为零提示图:
数字图像:
数值过长提示图:
1、开启LCD电源,初始化LCD
当中:时序发生器(TIMEGEN)
TIMEGEN产生LCD驱动器的控制信号。如VFRAME、VLINE、VCLK和VM。这些控制信号与REGBANK中的LCDCON1/2/3/4/5寄存器配制有着紧密关系。
基于这些可编程的REGBANK中LCD控制寄存器的配制,TIMEGEN能够产生合适的可编程控制信号来支持多种不同类型的LCD驱动器.
TFT屏的工作时序:
watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvbXV5YW5nX3Jlbg==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="">
VSYNC为帧同步信号。每发出一个脉冲表示新的一屏图像数据開始传输。
VSF=HSF÷[(VSPW+1)+(VBPD+1)+(VFPD+1)+(LINEVAL+1)]
HSYNC为行同步信号。每发出一个脉冲表示新的一行图像数据開始传输。
HSF=VCLK÷[(HSPW+1)+(HSPD+1)+(HFPD+1)+(HOZVAL+1)]
VCLK为像素同步信号,每发出一个脉冲表示新的一个点图像数据開始传输。
VCLK=HCLK÷[(CLKVAL+1)×2]
LCD显示是一帧一帧(一个画面)的,每一帧里显示又是从上到下一行一行的。每一行显示又是从左到右一个点一个点的。
而VSYNC,HSYNC,VCLK这些决定了他们的显示速度。
图中的VSPW,HSPW等决定对应脉冲的宽度。VBPD,HBPD决定了延时时间。
这些參数的设置都是由LCDCONn决定的。
初始化LCD:(设置TIMEGEN)
watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvbXV5YW5nX3Jlbg==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="">
/**************************************************************
TFT LCD功能模块初始化//此函数没开启屏蔽功能
**************************************************************/
void LCD_Init(void)
{
#define M5D(n) ((n)&0x1fffff)
#define LCD_ADDR ((U32)LCD_BUFFER)
//con1[6:5]显示模式选择为 TFT LCD面板 模式 [4:1]选择为 TFT的16bpp 像素模式
rLCDCON1 = (LCD_PIXCLOCK << 8) | (3 << 5) | (12 << 1);
//con2[23:14]设置高度320 VSPW[5:0]决定对应脉冲的宽度; VFPD[13:6]、VBPD[31:24]决定了延时时间; 选择option.h文件里T35定义參数
rLCDCON2 = (LCD_UPPER_MARGIN << 24) | ((LCD_HEIGHT - 1) << 14) | (LCD_LOWER_MARGIN << 6) | (LCD_VSYNC_LEN << 0);
//con3[18:8]设置高度240 HFPD、HBPD决定了延时时间; 选择option.h文件里T35定义參数
rLCDCON3 = (LCD_RIGHT_MARGIN << 19) | ((LCD_WIDTH - 1) << 8) | (LCD_LEFT_MARGIN << 0);
//con4 HSPW[8:0]决定对应脉冲的宽度; 选择option.h文件里T35定义參数
rLCDCON4 = (13 << 8) | (LCD_HSYNC_LEN << 0); #if !defined(LCD_CON5)
# define LCD_CON5 ((1<<11) | (1 << 9) | (1 << 8) | (1 << 3) | (1 << 0))
#endif
rLCDCON5 = LCD_CON5; rLCDSADDR1 = ((LCD_ADDR >> 22) << 21) | ((M5D(LCD_ADDR >> 1)) << 0);
rLCDSADDR2 = M5D((LCD_ADDR + LCD_WIDTH * LCD_HEIGHT * 2) >> 1);
rLCDSADDR3 = LCD_WIDTH; rLCDINTMSK |= 3; //中断屏蔽
rTCONSEL &= (~7); rTPAL = 0x0;
rTCONSEL &= ~((1<<4) | 1); }
使能LCD
/**************************************************************
LCD视频和控制信号输出或者停止,1开启视频输出
**************************************************************/
void Lcd_EnvidOnOff(int onoff)
{
if(onoff==1)
rLCDCON1|=1; // ENVID=ON
else
rLCDCON1 =rLCDCON1 & 0x3fffe; // ENVID Off
}
开启LCD电源
/**************************************************************
TFT LCD 电源控制引脚使能
**************************************************************/
void Lcd_PowerEnable(int invpwren,int pwren)
{
//GPG4 is setted as LCD_PWREN
rGPGUP = rGPGUP|(1<<4); // Pull-up disable
rGPGCON = rGPGCON|(3<<8); //GPG4=LCD_PWREN //Enable LCD POWER ENABLE Function
rLCDCON5 = rLCDCON5&(~(1<<3))|(pwren<<3); // PWREN
rLCDCON5 = rLCDCON5&(~(1<<5))|(invpwren<<5); // INVPWREN
}
2、开启触摸屏中断
/**************************************************************
TFT LCD *触摸屏中断函数*
**************************************************************/ void __irq Adc_Tc_Handler(void)
{ rADCTSC|=(1<<3)|(1<<2); //XP上拉电阻无效, 自己主动连续測量X坐标和Y坐标.
rADCCON|=(1<<0);//ADC转换開始 while(rADCCON&(1<<0));//检測ADC转换是否開始且ADCCON[0]自己主动清0
while(!(rADCCON&(0x1<<15))); //检測ADCCON[15]是否为1,ADC转换是否结束,(必须)
while(!(rINTPND&((U32)0x1<<31)));//检測ADC中断是否已请求 xdata=rADCDAT0&0x3ff;//读x坐标 >>xdata并非像素点,而是模拟信号 0-1000
ydata=rADCDAT1&0x3ff;//读y坐标 Uart_Printf("\n Xdata=%04d, Ydata=%04d\n", xdata, ydata); rSUBSRCPND|=(0x1<<9); //清除中断
rSRCPND|=((U32)0x1<<31);
rINTPND|=((U32)0x1<<31); rADCTSC =0xd3; //ADC等待中断模式
rADCTSC|=(0x1<<8); //ADCTSC[8]=1,设置抬起中断信号 while(!(rSUBSRCPND&(0x1<<9))); //检測触屏抬起中断是否已请求 rADCTSC &=~(0x1<<8);//ADCTSC[8]=0光标按下中断信号 // 因为以下这段代码和上面这段代码是看到大神们都会加上去的。调试得到
// 现象:上面的清除中断实现触屏中断,而以下这段则是加快中断后的响应
// (我的实验结果是:没以下的时候,触屏后的数值显示时间变长,蜂鸣器的
// 响声也变长,有种慢一拍的感觉) rSUBSRCPND|=(0x1<<9);
rSRCPND|=((U32)0x1<<31);
rINTPND|=((U32)0x1<<31);
} void Touch_Init(void)
{
rADCCON=((1<<14)|(9<<6)); //A/D分频时钟有效,其值为9
rADCTSC=0xd3; //光标按下中断信号,YM有效,YP无效,XM有效,XP无效,XP上拉电阻,普通ADC转换,等待中断模式
rADCDLY=50000; //正常转换模式转换延时大约为(1/3.6864M)*50000=13.56ms rINTSUBMSK &=~(0x1<<9);//TC中断使能
rINTMSK &=~((U32)0x1<<31);//ADC总中断使能 pISR_ADC=(U32)Adc_Tc_Handler;//指向中断向量表 }
3、获取键值
并定义变量botten1存储键值,flag1按键标记。flag2运算标记
/**************************************************************
------------获取键值--------------
**************************************************************/
void get_key(void){
//数字块
if( xdata >= 70 && xdata <= 285 && ydata >= 100 && ydata < 262 ) //0
{ Beep(2000, 100);botten1 = 0;flag1=1;xdata = ydata = 0; }
else if( xdata >= 70 && xdata <= 285 && ydata >= 263 && ydata < 425 ) //1
{ Beep(2000, 100);botten1 = 1;flag1=1;xdata = ydata = 0; }
else if( xdata >= 285 && xdata <= 500 && ydata >= 263 && ydata < 425 ) //2
{ Beep(2000, 100);botten1 = 2;flag1=1;xdata = ydata = 0; }
else if( xdata >= 500 && xdata <= 715 && ydata >= 263 && ydata < 425 ) //3
{ Beep(2000, 100);botten1 = 3;flag1=1;xdata = ydata = 0; }
else if( xdata >= 70 && xdata <= 285 && ydata >= 425 && ydata < 587 ) //4
{ Beep(2000, 100);botten1 = 4;flag1=1;xdata = ydata = 0; }
else if( xdata >= 285 && xdata <= 500 && ydata >= 425 && ydata < 587 ) //5
{ Beep(2000, 100);botten1 = 5;flag1=1;xdata = ydata = 0; }
else if( xdata >= 500 && xdata <= 715 && ydata >= 425 && ydata < 587 ) //6
{ Beep(2000, 100);botten1 = 6;flag1=1;xdata = ydata = 0; }
else if( xdata >= 70 && xdata <= 285 && ydata >= 587 && ydata < 750 ) //7
{ Beep(2000, 100);botten1 = 7;flag1=1;xdata = ydata = 0; }
else if( xdata >= 285 && xdata <= 500 && ydata >= 587 && ydata < 750 ) //8
{ Beep(2000, 100);botten1 = 8;flag1=1;xdata = ydata = 0; }
else if( xdata >= 500 && xdata <= 715 && ydata >= 587 && ydata < 750 ) //9
{ Beep(2000, 100);botten1 = 9;flag1=1;xdata = ydata = 0; }
else
//功能运算块
if( xdata >= 715 && xdata <= 930 && ydata >= 100 && ydata < 262 ) //除
{ Beep(2000, 100);botten1 = '/';flag1=1;flag2=1;xdata = ydata = 0; }
else if( xdata >= 715 && xdata <= 930 && ydata >= 263 && ydata < 425 ) //乘以
{ Beep(2000, 100);botten1 = '*';flag1=1;flag2=2;xdata = ydata = 0; }
else if( xdata >= 715 && xdata <= 930 && ydata >= 425 && ydata < 587 ) //减法
{ Beep(2000, 100);botten1 = '-';flag1=1;flag2=3;xdata = ydata = 0; }
else if( xdata >= 715 && xdata <= 930 && ydata >= 587 && ydata < 750 ) //加法
{ Beep(2000, 100);botten1 = '+';flag1=1;flag2=4;xdata = ydata = 0; }
else
if( xdata >= 500 && xdata <= 715 && ydata >= 100 && ydata < 262 ) //等于
{ Beep(2000, 100);botten1 = '=';flag1=1;xdata = ydata = 0; }
else
if( xdata >= 285 && xdata <= 500 && ydata >= 100 && ydata < 262 ) // 清空
{ Beep(2000, 100);botten1 = 'c';flag1=1;xdata = ydata = 0; }
}
4、区分键值来调用数字图片显示
/**************************************************************
------------处理键值--------------
**************************************************************/
void resout(){ if(flag2==4) {sum1=sum1+sum2; show_picturu(sum1); sum1=0;sum2=0;flag2=0; } //依据标志flag2 进行对应的 sum1=sum1 ? sum2 的运算,运算完sum1 sum2置零
else if(flag2==3) {sum1=sum1-sum2; show_picturu(sum1); sum1=0;sum2=0;flag2=0; }
else if(flag2==2){sum1=sum1*sum2; show_picturu(sum1); sum1=0;sum2=0;flag2=0; }
else if(flag2==1){
if(sum2==0) {sum1=0;sum2=0;flag2=0; Pait_Bmp(1, 34, 236, 30, error);Delay(500);show_picturu(0);} //对除数为0处理。
else {sum1=sum1/sum2;show_picturu(sum1); sum1=0;sum2=0;flag2=0; }} //注意:除法运算结果会舍去小数部分 }
void cleaning(){
sum1=0,sum2=0;flag2=0;show_picturu(0);
}
void show_num(void){
while(flag1){
flag1=0; //标志置零
switch(botten1){
case 0:
case 1:
case 2:
case 3:
case 4:
case 5:
case 6:
case 7:
case 8:
case 9:{sum2=sum2*10+botten1;
if(sum2>999999999){
sum2=0;Pait_Bmp(2, 34, 236, 30, numerror);
Delay(500);show_picturu(sum2);
}
else show_picturu(sum2);
} break; //按键值存于 sum2 case '+':
case '-':
case '*':
case '/': sum1=sum2,sum2=0; break; //sum2值转存于sum1,sum2置零 case '=': resout(); break; //之前把以下的这段放在这里,观察变量发现sum1和和sum2到这里就置零了(按下=后永远等于0),无奈之下试试把推断放进一个函数 resout(); 里看看。结果成功了! !。
/* if(flag2==4) {show_picturu(sum1+sum2); sum2=0;flag2=0;} //依据标志flag2 进行对应的 sum1=sum1 ? sum2 的运算
else if(flag2==3) {show_picturu(sum1-sum2); sum2=0;flag2=0; }
else if(flag2==2){show_picturu(sum1*sum2); sum2=0;flag2=0; }
else if(flag2==1){
if(sum2==0) {sum1=0;sum2=0;flag2=0; Pait_Bmp(1, 34, 236, 30, error);Delay(500);show_picturu(0);} //对除数为0处理。
else {show_picturu(sum1/sum2); sum2=0;flag2=0; }} //注意:除法运算结果会舍去小数部分
*/ case 'c': cleaning(); break;
} }
}
5、调用图片
<span style="font-size:10px;">/**************************************************************
------------调用图片函数--------------
**************************************************************/
void show_picturu(int sum){
int k=0,j=0;
Pait_Bmp(1, 34, 238, 30, clean);
if(sum>0){ //数值大于0时
for(;sum>0;){
k=sum%10; //k用来取余数
sum=sum/10; //num舍去最后一位
++j; //j用来标志k的余数在原数值中的实际位数
numTOpic(k,j);
}
}
else if(sum==0){ //数值等于0时
numTOpic(0,1);
}
else if(sum<0){ //数值小于0时
sum=-sum;
for(;sum>0;){
k=sum%10; //k用来取余数
sum=sum/10; //num舍去最后一位
++j; //j用来标志k的余数在原数值中的实际位数
numTOpic(k,j);
}
Pait_Bmp(238-13*(j+1), 34, 13, 30, num_);
} }
void numTOpic(int m ,int n){
switch(m){
case 0:Pait_Bmp(238-13*n, 34, 13, 30, num0);break;
case 1:Pait_Bmp(238-13*n, 34, 13, 30, num1);break;
case 2:Pait_Bmp(238-13*n, 34, 13, 30, num2);break;
case 3:Pait_Bmp(238-13*n, 34, 13, 30, num3);break;
case 4:Pait_Bmp(238-13*n, 34, 13, 30, num4);break;
case 5:Pait_Bmp(238-13*n, 34, 13, 30, num5);break;
case 6:Pait_Bmp(238-13*n, 34, 13, 30, num6);break;
case 7:Pait_Bmp(238-13*n, 34, 13, 30, num7);break;
case 8:Pait_Bmp(238-13*n, 34, 13, 30, num8);break;
case 9:Pait_Bmp(238-13*n, 34, 13, 30, num9);break;
}
}
</span>
附:
硬件环境:J-link v8、mini2440、J-link转接板、串口转USB线、T35 TFT LCD屏
软件环境:windows7(32位)、开发板uboot(NandFlash)、J-link驱动(J-Link ARM V4.10i)、SecureCRT、ADS1.2
完整项目下载
版权声明:本文博客原创文章,博客,未经同意,不得转载。
mini2440裸试验—计算器(LCD显示,触摸屏突破)的更多相关文章
- 【Mood-6】空气显示触摸屏、智能钱夹
空气显示触摸屏 这款屏幕借助从设备中送出的空气和水在空中形成投影,可以用来展示计算机或平板中的图像.此外,它还可以实现人机互动.你只需在虚拟屏幕前挥动双手,就能完成一系列的隔空操作,如滑动.捏合.缩放 ...
- LCD显示方向
一.ILI9341内存到显示地址的映射 本文只讨论“正常显示”,不讨论“垂直滚动显示”模式. 可以看到物理内存被两个指针访问,行指针和列指针,行指针范围从000h到013Fh,列指针范围为0000h到 ...
- Raspberry PI Model B+ (LCD显示CPU温度)
Title:Raspberry PI Model B+ (LCD显示CPU温度) --2015-01-29 17:44 买了块连接Raspberry PI Model B+的LCD显示器,上面没写C ...
- 逆向project第004篇:令计算器程序显示汉字(下)
一.前言 钩子技术是一项很有有用价值的技术.在Windows下HOOK技术的方法比較多,使用比較灵活,常见的应用层的HOOK方法有Inline HOOK(详见<反病毒攻防研究第012篇:利用In ...
- LCD显示GPS时钟[嵌入式系统]
夏任务102:做一个GPS钟 实验要求 用RPi的串口连接一个GPS模块,从GPS得到实时时间,在7段数码管或LCD上显示 实验工具: Raspberry Pi Model B主机, 8G c10 S ...
- 2.数码相框-编码(ASCII/GB2312/Unicode)介绍,并使LCD显示汉字字符(2)
在上章-学习了数码相框的框架分析(1)了 本章主要内容如下: 1)熟悉ASCII/GB2312/Unicode编码 2)写应用程序,使LCD显示汉字和字符 大家都知道,数据传输的是二进制,而字符和汉字 ...
- LCD显示异常分析——撕裂(tear effect)【转】
转自:LCD显示异常分析--撕裂(tear effect) 概述 在上一篇<LCD显示异常分析--开机闪现花屏>中,我们一起分析了开机花屏的问题,在这一篇中,我将对LCD撕裂(tear e ...
- LCD显示异常分析——开机闪现花屏【转】
转自LCD显示异常分析--开机闪现花屏 最近在工作中,有同事遇到LCD开机瞬间会闪现雪花屏的问题,而这类问题都有个共同点,那就是都发生在带GRAM的屏上,同样的问题,在休眠唤醒时也会出现. 其实这类问 ...
- TFT LCD显示原理详解
<什么是液晶> 我们一般认为物体有三态:固态.液态.气态,其实这只是针对水而言,有一些有机化和物 还有介于固态和液态中间的状态 就是液晶态,如下图(一): ...
随机推荐
- 【转】有效修改max open files/ulimit -n
[转]有效修改max open files/ulimit -n_追梦20121222_新浪博客 [转]有效修改max open files/ulimit -n (2011-11-18 0 ...
- POJ 2632 Crashing Robots (坑爹的模拟题)
Crashing Robots Time Limit: 1000MS Memory Limit: 65536K Total Submissions: 6599 Accepted: 2854 D ...
- 12306 Android客户端的libcheckcode.so解密及修复
源:http://blog.csdn.net/justfwd/article/details/45219895 这篇文章纯粹属于安全分析研究,请勿用于非法用途.如有侵犯到厂家,请告知作者删除 123 ...
- ASP.NET 常用内置对象详解-----Response
利用提供的内置对象,可以实现页面之间的数据传递及实现一些特定的功能,如:缓冲输出,页面重定向等等. Response :响应,反应 Request:请求 Server:服务器 Application: ...
- Repeater
- sublime_text 破解
之前一直使用vi的,但是总觉的vi差了一点什么,不够现代化,老古董了.没办法,只是因为vi在linux下面是预装的,有些时候必须使用vi. 不过除了这种情况之外,vi的可配置性比较高,但是在使用了一段 ...
- SystemParametersInfo API学习(128个中文参数解释,215个实际值)
uiAction:该参数指定要查询或设置的系统级参数.其取值如下:SPI_GETACCESSTIMEOUT:检索与可访问特性相关联的超时段的信息,PvParam参数必须指向某个ACCESSTIMEOU ...
- 怎样在Android实现桌面清理内存简单Widget小控件
怎样在Android实现桌面清理内存简单Widget小控件 我们常常会看到类似于360.金山手机卫士一类的软件会带一个widget小控件,显示在桌面上,上面会显示现有内存大小,然后会带一个按键功能来一 ...
- codeforces 604A Uncowed Forces
题目链接:http://codeforces.com/problemset/problem/604/A 题意:求cf比赛每次能够增加的排名,运算规则会告诉你 题目分类:数学 题目分析:用题目给的公式直 ...
- JAVA WEB开发环境搭建教程
一.下载安装JDK,配置好环境变量.(例如我JDK安装的目录为:C:\Program Files (x86)\Java\jdk1.6.0_10 ) 点击我的电脑-属性-系统设置(高级系统设置) ...