基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转的项目
一、前言
1、基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转的项目包括用Keil软件编写单片机C语言程序和用Proteus软件仿真单片机外围电路
2、基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转项目构思
(1)、实现什么功能:LCD1602字符型液晶显示器先显示时分秒,在点击移位按键后,停止计时,LCD1602字符型液晶显示器光标闪烁,每次按下移位键,LCD1602字符型液晶显示器光标随每次按下移位键移位到时分秒个位十位处闪烁,当LCD1602字符型液晶显示器的时分秒个位十位有闪烁后,可修改LCD1602字符型液晶显示器的时分秒个位十位闪烁位上的数值,再通过移位按键或启停按键启动或停止计时。
(2)、如何实现功能:如何让LCD1602字符型液晶显示器先显示时分秒:采用定时器0工作方式1计时,计时得到的数值赋给LCD1602字符型液晶显示器显示时间两位数分解函数进行分解,分解得到的个位数值与十位数值用变量代替分别由LCD1602字符型液晶显示器写指令函数和LCD1602字符型液晶显示器写数据函数写入LCD1602字符型液晶显示器,通过LCD1602字符型液晶显示器显示出来。如何让LCD1602字符型液晶显示器的时分秒个位十位闪烁:采用按键扫描函数扫描,每次按下移位键(此时定时器0停止计时),执行LCD1602字符型液晶显示器光标闪烁指令和LCD1602字符型液晶显示器光标随每次按下移位键移位到时分秒个位十位处闪烁的位置指令。如何修改LCD1602字符型液晶显示器的时分秒个位十位闪烁位数值并在原计时基础上实现计时:当移位键按下后,定时器0停止计时,计时得到的数值采用两位数分解公式(如:shi=num/10,ge=num%10。)进行分解,分解得到的个位数值与十位数值用变量代替写入按键扫描函数,此时也要采用两位数合成公式(如:miao=shi+ge=(num/10)*10+num%10)求出原先的计时数值,用变量代替原先的计时数值写入按键扫描函数(原因:时分秒的个位或十位显示位的数值是在原计时数值上分解得来,当时分秒的个位或十位显示位的数值发生变化后,原计时数值也要变化,否则启动定时器0计时后,LCD1602字符型液晶显示器显示的是原计时时间,而不是修改时分秒的个位或十位显示位的数值后的计时,因此要采用两位数合成公式(miao=shi+ge=(num/10)*10+num%10)求出原先的计时数值,用变量代替原先的计时数值写入按键扫描函数。)。
二、基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转项目的Keil软件编写的单片机C语言程序
#include<reg52.h>
#define uchar unsigned char
#define uint unsigned int
sbit qitingjian=P1^0;
sbit zhengzhuan=P1^1;
sbit fanzhuan=P1^2;
sbit jiasujian=P1^3;
sbit jiansujian=P1^4;
sbit IN1=P1^5;
sbit IN2=P1^6;
sbit ENA=P1^7;
sbit duan=P3^0;
sbit wei=P3^1;
sbit qitingled=P3^4;
sbit zhengzhuanled=P3^5;
sbit fanzhuanled=P3^6;
sbit zhuansuled=P3^7;
sbit waibuzhongduanling=P3^2;
uint qian,bai,shi,ge,zhuansu;
uint maichongcount,Time0num,Time1num,pwm,qitingnum,zhengzhuanflag,fanzhuanflag;
uchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x27,0x7f,0x6f,0x40,0x7c,0x39,0x5e,0x79,0x71,0x00};
uchar code weima[]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf,0xbf,0x7f,0xff};
void delay(uint jishi);
void TimerInit();
void Time0();
void Time1();
void KeyScan();
void waibuzhongduanlingjishu();
void shumaguandisplay(uint qian,uint bai,uint shi,uint ge);
void shumaguannodisplay(uint qian,uint bai,uint shi,uint ge);
void main()
{
TimerInit();
IN1=0;
IN2=0;
while(1)
{
KeyScan();
if(qitingnum==1)
shumaguandisplay(qian,bai,shi,ge);
}
}
void delay(uint jishi)
{
uint i,j;
for(i=jishi;i>0;i--)
for(j=110;j>0;j--);
}
void TimerInit()
{
TMOD=0x11;
TH0=(65536-1000)/256;
TL0=(65536-1000)%256;
TH1=(65536-50000)/256;
TL1=(65536-50000)%256;
EA=1;
ET0=1;
TR0=1;
EX0=1;
IT0=1;
ET1=1;
TR1=1;
}
void Time0() interrupt 1
{
TH0=(65536-1000)/256;
TL0=(65536-1000)%256;
Time0num++;
if(Time0num==20)
{
Time0num=0;
}
if(Time0num<pwm)
{
ENA=1;
zhuansuled=0;
}
else
{
ENA=0;
zhuansuled=1;
}
}
void Time1() interrupt 3
{
TH1=(65536-50000)/256;
TL1=(65536-50000)%256;
Time1num++;
if(Time1num==20)
{
Time1num=0;
EX0=0;
zhuansu=55*maichongcount/24;
qian=zhuansu/1000;
bai=zhuansu%1000/100;
shi=zhuansu%100/10;
ge=zhuansu%10;
maichongcount=0;
EX0=1;
}
}
void waibuzhongduanlingjishu() interrupt 0 using 1
{
maichongcount++ ;
}
void KeyScan()
{
if(qitingjian==0)
{
shumaguandisplay(qian,bai,shi,ge);
if(qitingjian==0)
{
while(!qitingjian)
shumaguandisplay(qian,bai,shi,ge);
qitingnum++;
qitingled=0;
if(qitingnum==2)
{
qitingnum=0;
qitingled=1;
zhengzhuanled=1;
fanzhuanled=1;
zhuansuled=1;
zhengzhuanflag=0;
fanzhuanflag=0;
IN1=0;
IN2=0;
shumaguannodisplay(qian,bai,shi,ge);
}
}
}
if(qitingnum==1)
{
if(zhengzhuan==0)
{
shumaguandisplay(qian,bai,shi,ge);
if(zhengzhuan==0)
{
while(!zhengzhuan)
shumaguandisplay(qian,bai,shi,ge);
zhengzhuanled=0;
fanzhuanled=1;
zhengzhuanflag=1;
fanzhuanflag=0;
IN1=1;
IN2=0;
}
}
if(fanzhuan==0)
{
shumaguandisplay(qian,bai,shi,ge);
if(fanzhuan==0)
{
while(!fanzhuan)
shumaguandisplay(qian,bai,shi,ge);
zhengzhuanled=1;
fanzhuanled=0;
zhengzhuanflag=0;
fanzhuanflag=1;
IN1=0;
IN2=1;
}
}
}
if(zhengzhuanflag==1||fanzhuanflag==1)
{
if(jiasujian==0)
{
shumaguandisplay(qian,bai,shi,ge);
if(jiasujian==0)
{
while(!jiasujian)
shumaguandisplay(qian,bai,shi,ge);
if(pwm < 20)
pwm++;
if(pwm >= 20)
pwm = 19;
}
}
if(jiansujian==0)
{
shumaguandisplay(qian,bai,shi,ge);
if(jiansujian==0)
{
while(!jiansujian)
shumaguandisplay(qian,bai,shi,ge);
if(pwm > 0)
pwm--;
if(pwm <= 0)
pwm = 0;
}
}
}
}
void shumaguandisplay(uint qian,uint bai,uint shi,uint ge)
{
duan=1;
P0=table[qian];
duan=0;
P0=0x00;
wei=1;
P2=weima[0];
wei=0;
delay(1);
duan=1;
P0=table[bai];
duan=0;
P0=0x00;
wei=1;
P2=weima[1];
wei=0;
delay(1);
duan=1;
P0=table[shi];
duan=0;
P0=0x00;
wei=1;
P2=weima[2];
wei=0;
delay(1);
duan=1;
P0=table[ge];
duan=0;
P0=0x00;
wei=1;
P2=weima[3];
wei=0;
delay(1);
}
void shumaguannodisplay(uint qian,uint bai,uint shi,uint ge)
{
duan=1;
P0=table[qian];
duan=1;
P0=0x00;
wei=1;
P2=weima[0];
wei=1;
delay(1);
duan=1;
P0=table[bai];
duan=1;
P0=0x00;
wei=1;
P2=weima[1];
wei=1;
delay(1);
duan=1;
P0=table[shi];
duan=1;
P0=0x00;
wei=1;
P2=weima[2];
wei=1;
delay(1);
duan=1;
P0=table[ge];
duan=1;
P0=0x00;
wei=1;
P2=weima[3];
wei=1;
delay(1);
}
三、基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转项目的Proteus软件仿真单片机外围电路

四、基于51单片机PWM(即脉冲宽度调制)调速数码管显示测速L298芯片控制直流电机正反运转项目的操作功能描述
(1)、不修改时分秒个位十位数值,只是启动或停止计时的情况:如果第一次按下移位键,则停止计时,启动计时可按下移位键7次或按下启停键,再次停止计时可按下移位键或按下启停键,再次启动计时可按下移位键7次或按下启停键,周而复始。如果第一次按下启停键,则停止计时,启动计时可按下移位键7次或按下启停键,再次停止计时可按下移位键或按下启停键,再次启动计时可按下移位键7次或按下启停键,周而复始。
(2)、修改时分秒个位十位数值,再启动或停止计时的情况:要修改时分秒个位十位上的数值,再启动或停止计时,首先必须按下移位键,此时停止计时,通过点击移位键让LCD1602字符型液晶显示器光标移到时分秒相应个位十位数值上,利用点击增加键或减少键修改数值,修改完毕后,启动计时可按下移位键多次让LCD1602字符型液晶显示器光标回到秒钟个位数值上或按下启停键,停止计时可按下移位键或按下启停键,当按下移位键时,又可修改时分秒个位十位上的数值,再次启动计时可按下移位键多次让LCD1602字符型液晶显示器光标回到秒钟个位数值上或按下启停键,周而复始。