新手上路
- 积分
- 29
- 金钱
- 29
- 注册时间
- 2017-4-11
- 在线时间
- 5 小时
|
1金钱
在下愚笨,实在找不出哪里有问题,但是显示就是不正常,编译无错误无警告。另外,想请教一下,在下的中断有问题吗,为什么开了中断就会出现问题呢。还有,绿色标注的部分如果放进大循环里,12864就会一直闪不停啊,这也不是在下想要的结果啊。因程序稍长,但程序很简单,希望您花几分钟看一下,重点部分红色标注,其余都是一些简单的驱动,下面程序的加热功能区也不需要看。
简单说明一下,在下想要实现的功能。在下打算是用一个部分矩阵键盘和12864在模拟显示个简单太阳能控制器。按键不同,来实现不同的功能选择。用杜邦线引脚的原因是,想来模拟一下水位过低的情况,触发自动上水功能,用中断来模拟上水,每5s,增长一个百分点。大体情况就是这样,如有疑问,随时传唤在下。
代码不美且较长,望您能指点迷津,感激不尽!
#include<reg52.h>
#include <stdlib.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
#define LCD_data P0
#define delayNOP(); {_nop_();_nop_();_nop_();_nop_();};
#define N 12
sbit col1=P1^7; //列端口定义
sbit col2=P1^6;
sbit col3=P2^0;
sbit col4=P2^1;
sbit LCD_EN=P3^4;
sbit LCD_RS=P3^5;
sbit LCD_RW=P3^6;
sbit LCD_PSB=P3^7;
sbit _Speak=P3^2 ; //讯响器控制脚
sbit Low=P3^0; //模拟最低水位触发脚
uchar code dis0[]={"****智能控制****"};
uchar code dis1[]={"当前功能显示区"};
uchar code dis2[]={"当前水温: "};
uchar code dis3[]={"当前水位比: 60"};
uchar code dis4[]={"按S19 开始上水"};
uchar code dis5[]={"目标水位比: "};
uchar code dis6[]={"按 S7 停止上水"};
uchar code dis7[]={"上水中..."};
uchar code dis8[]={"按S20 开始加热"};
uchar code dis9[]={"目标水温:"};
uchar code dis10[]={"按 S8 停止加热"};
uchar code dis11[]={"加热中..."};
uchar code dis12[]={"目标水位比: 00"};
uchar code dis13[]={"当前水位比: "};
void delay1ms(uint);
void delay(uchar);
void keyscan();
void write_cmd(uchar cmd);
void write_dat(uchar dat);
void lcd_pos(uchar X,uchar Y);
void write_sfm1(uchar add,uchar date);
void write_sfm2(uchar add,uchar date);
void lcd_init();
bit lcd_busy();
char filter();
uint num=0,i=0;
uint counter=0,a=0,counter1=0,b=0;
uint water0=0,water1=0,temp=0;
uint m=0;
uint LOW=0;
void main()//固定界面显示
{
TH0=(65536-46080)/256;
TL0=(65536-46080)%256; //50ms定时
ET0=1;
EA=1;
lcd_busy();
delay1ms(10);
lcd_init();
lcd_pos(0,0);//智能控制
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
lcd_pos(1,0);//当前水温
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
lcd_pos(2,0);//当前水位比
i=0;
while(dis3!='\0')
{
write_dat(dis3);
i++;
}
lcd_pos(3,0);//当前功能显示区
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
delay1ms(10);
while(1)
{
/*if(Low==1)
{
LOW=1;
}
else if(Low==0)
{
LOW=0;
}
else
{
LOW=2;
}*/
if(Low==0)//触发模拟自动上水
{
TR0=1;//开中断
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis6!='\0')
{
write_dat(dis6);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
if(water1<=water0)//判断是否上水完毕
{
lcd_pos(2,6);
write_sfm1(6,water1);
write_cmd(0x90);
m=0xfe;
P1=m;
delay1ms(500); //延时
m=_crol_(m,1);
}
else if(water1>water0)
{
TR0=0;//关中断
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis4!='\0')
{
write_dat(dis4);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
lcd_pos(2,6);
write_sfm1(6,water0);
write_cmd(0x90);
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis7!='\0')
{
write_dat(dis7);
i++;
}
}
else if(Low==1)//未触发
{
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
lcd_pos(2,6);
write_sfm1(6,water0);
write_cmd(0x90);
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
}
keyscan();
}
}
void delay1ms(uint x)//延时
{
uint i,j;
for(j=0;j<x;j++)
for(i=0;i<110;i++);
}
void delay(uchar i)//延时
{
uchar j,k;
for(j=i;j>0;j--)
for(k=125;k>0;k--);
}
void keyscan()
{
col1=1;col2=1;col3=0;col4=1;//上水按键区
temp=P2;
temp=P2&0x3f;
if(col3==0)
{
delay(80);
if(temp!=0x3f)
{
temp=P2&0x3c;
switch(temp)
{
case 0x1c: //进入上水功能界面
counter++;
a=counter%2;
switch(a)
{
case 1: //第一功能键,显示上水界面
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis4!='\0')
{
write_dat(dis4);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis12!='\0')
{
write_dat(dis12);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0: //第二功能键,开始上水
TR0=1;
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis6!='\0')
{
write_dat(dis6);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
lcd_pos(2,6);
write_sfm1(6,water1);
write_cmd(0x90);
delay(20);
lcd_pos(3,0);
i=0;
while(dis7!='\0')
{
write_dat(dis7);
i++;
}
if(water1<=water0)
{
m=0xfe;
P1=m;
delay1ms(500); //延时
m=_crol_(m,1);
}
else
{
TR0=0;
}
break;
}
counter=0;
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
lcd_pos(2,6);
write_sfm1(6,water0);
write_cmd(0x90);
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0x2c: //增加水位比
_Speak=0;
delay1ms(40);
_Speak=1;
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis4!='\0')
{
write_dat(dis4);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis12!='\0')
{
write_dat(dis12);
i++;
}
lcd_pos(2,6);
water1++;
if(water1==100)
{
water1=99;
_Speak=0;
delay1ms(100);
_Speak=1;
P1=0x00;
delay1ms(100);
P1=0xff;
}
write_sfm1(6,water1);
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0x34: //降低水位比
_Speak=0;
delay1ms(40);
_Speak=1;
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis4!='\0')
{
write_dat(dis4);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis12!='\0')
{
write_dat(dis12);
i++;
}
lcd_pos(2,6);
water1--;
if(water1==0)
{
water1=1;
_Speak=0;
delay1ms(100);
_Speak=1;
P1=0x00;
delay1ms(100);
P1=0xff;
}
write_sfm1(6,water1);
write_cmd(0x88);
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0x38: //退出键以及上水中止键
TR0=0;
counter=0;
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
if(a==1)
{
delay(20);
lcd_pos(2,0);
i=0;
while(dis3!='\0')
{
write_dat(dis3);
i++;
}
}
else if(a==0)
{
delay(20);
lcd_pos(2,0);
i=0;
while(dis13!='\0')
{
write_dat(dis13);
i++;
}
lcd_pos(2,6);
write_sfm1(6,water1);
write_cmd(0x90);
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
P1=0xff;
break;
}
}
}
col1=1;col2=1;col3=1;col4=0; //加热按键区
temp=P2;
temp=P2&0x3f;
if(col4==0)
{
delay(80);
if(temp!=0x3f)
{
temp=P2&0x3c;
switch(temp)
{
case 0x1c: //进入加热功能界面
counter1++;
b=counter1%2;
switch(b)
{
case 1: //第一功能键,显示加热界面
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis9!='\0')
{
write_dat(dis9);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis8!='\0')
{
write_dat(dis8);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0: //第二功能键,开始加热
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis10!='\0')
{
write_dat(dis10);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis11!='\0')
{
write_dat(dis11);
i++;
}
break;
}
break;
case 0x2c: //提高温度
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis9!='\0')
{
write_dat(dis9);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis8!='\0')
{
write_dat(dis8);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0x34: //降低温度
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis9!='\0')
{
write_dat(dis9);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis8!='\0')
{
write_dat(dis8);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
case 0x38: //退出键以及加热中止键
write_cmd(0x01);
delay1ms(5);
delay(20);
lcd_pos(0,0);
i=0;
while(dis0!='\0')
{
write_dat(dis0);
i++;
}
delay(20);
lcd_pos(1,0);
i=0;
while(dis2!='\0')
{
write_dat(dis2);
i++;
}
delay(20);
lcd_pos(2,0);
i=0;
while(dis3!='\0')
{
write_dat(dis3);
i++;
}
delay(20);
lcd_pos(3,0);
i=0;
while(dis1!='\0')
{
write_dat(dis1);
i++;
}
break;
}
}
}
while(temp!=0x3c)
{
temp=P2;
temp=temp&0x3c;
}
}
bit lcd_busy()//检测忙状态
{
bit result;
LCD_RS = 0;
LCD_EN = 1;
delayNOP();
result = (bit)(P0&0x80);
LCD_EN = 0;
return(result);
}
void write_cmd(uchar cmd)//写指令数据到LCD
{
LCD_RS=0;
LCD_RW=0;
LCD_EN=0;
P0=cmd;
delay1ms(5);
LCD_EN=1;
delay1ms(5);
LCD_EN=0;
}
void write_dat(uchar dat)//写显示数据到LCD
{
LCD_RS=1;
LCD_RW=0;
LCD_EN=0;
P0=dat;
delay1ms(5);
LCD_EN=1;
delay1ms(5);
LCD_EN=0;
}
void lcd_pos(uchar X,uchar Y)//设定显示位置
{
uchar pos;
if(X==0)
{X=0x80;}
else if(X==1)
{X=0x90;}
else if(X==2)
{X=0x88;}
else if(X==3)
{X=0x98;}
pos=X+Y;
write_cmd(pos);
}
void write_sfm1(uchar add,uchar date)//显示数据1,中断外部使用
{
uchar shi,ge;
shi=date/10;
ge=date%10;
write_cmd(0x88+add);
write_dat(0x30+shi);
write_dat(0x30+ge);
}
void lcd_init()//LCD初始化
{
LCD_PSB=1;
write_cmd(0x30);
delay1ms(5);
write_cmd(0x0c);
delay1ms(5);
write_cmd(0x01);
delay1ms(5);
write_cmd(0x38);
delay1ms(5);
}
void Time0(void) interrupt 1 using 0
{
TH0=(65536-46080)/256;
TL0=(65536-46080)%256;
delay1ms(4950);
water1++;
}
望您指点迷津,谢谢您了!
|
|