标题:
作为一个初学者,如何学好单片机,课堂上的内容过于粗浅 求帮助
[打印本页]
作者:
317729178
时间:
2019-5-19 10:58
标题:
作为一个初学者,如何学好单片机,课堂上的内容过于粗浅 求帮助
作为一个初学者,如何学好单片机,课堂上的内容过于粗浅
单片机源程序如下:
/*---------------------------------------------------------------
项目名称:自动售水机系统
----------------------------------------------------------------*/
#include"reg52.h"
#include"pcf8591.h"
#include"iic.h" //iic协议
#include"ct107.h" //CT107单片机初始化
#include"deplay.h" //延时
#define AddWr 0x90 //写数据地址
#define AddRd 0x91 //读数据地址
sbit key6=P3^1; //定义按键端口
sbit key7=P3^0;
unsigned char code smg_du[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90}; //数码管段选“0~9”
unsigned char code smg_we[]={0x01,0x02,0x04,0x08,0x10,0x20,0x40,0x80}; //数码管位选
unsigned char tab[8]={0,0,5,0,0,0,0,0}; //显示数组
unsigned int water,total; //定义水量,总价
float price; //定义单价
unsigned char light; //定义光照强度变量
bit flag,flag1,flag2; //定义标志位
unsigned char ReadADC(unsigned char Ch1); //读AD函数,Ch1为通道号,取值0~3;
void diswork(); //数据处理函数
main()
{
price=0.5; //设定单价为0.5元/L
TMOD=0x11; //设置定时器0,1为16位定时器
TH0=(65536-50000)/256; //设定定时器0初值50ms,用于累计水量
TL0=(65536-50000)%256;
TH1=(65536-2000)/256; //设定定时器0初值2ms,用于扫描数码管和L1
TL1=(65536-2000)%256;
TR1=1; //开定时器1
TR0=1; //开定时器0
ET1=1; //开定时器1中断允许位
EA=1; //开总中断
ct107_init();
while(1) //停止
{
if(!key6) //判断按键是否按下
{
deplay_50us(200); //消抖
if(!key6) //确认按键按下
{
ET0=0;
P2&=0x1f;
RELAY=0; //关继电器
BUZZ=0; //避免蜂鸣器的影响
P2|=Y5C;
P2&=0x1f;
flag=1; //停止标志位
flag2=0; //按下停止后把许可启动标志位置0,方可进入下次启动
}
}
if(!flag2) //许可启动标志位为0才可启动
if(!key7) //启动
{
deplay_50us(200);
if(!key7)
{
ET0=1;
water=0; //水量清0
total=0; //总价清0
P2&=0x1f;
RELAY=1; //开继电器
BUZZ=0;
P2|=Y5C;
P2&=0x1f;
flag=0; //复位停止标志位
flag2=1; //置位许可启动标志位防止再次进入启动程序
}
}
diswork(); //显示数据处理
light=ReadADC(1); //读AD数据(光敏电阻)
if(light<64) //判断电压是否下于1.25V。1.25*255/5=64
flag1=1;
else
flag1=0;
}
}
void diswork()
{
if(flag) //停止时显示总价,启动时显示水量
{
total=(unsigned int)(water*price);
tab[4]=total/1000;
tab[5]=total%1000/100;
tab[6]=total%100/10;
tab[7]=total%10;
}
else
{
tab[4]=water/1000;
tab[5]=water%1000/100;
tab[6]=water%100/10;
tab[7]=water%10;
}
}
unsigned char ReadADC(unsigned char Ch1) //读通道Ch1的数据
{
unsigned char Data;
init_iic();
Start();
Send(AddWr);
Ack();
Send(0x40|Ch1);
Ack();
Start();
Send(AddRd);
Ack();
Data=Read();
Scl=0;
NoAck();
Stop();
return Data;
}
void timeint_0() interrupt 1 //定时器0中断用于计算水量,其中断优先级比定时器1中断高,防止了中断被打断,使数据更准确
{
static unsigned char k;
TH0=(65536-50000)/256; //每50ms进一次中断
TL0=(65536-50000)%256;
if(k) //每100ms水量增加10mL
{
k=0;
if(water==9999)
{
ET0=0;
P2&=0x1f;
RELAY=0;
BUZZ=0;
P2|=Y5C;
P2&=0x1f;
flag=1;
flag2=0;
}
else
water++;
}
else
k++;
}
void timeint_1() interrupt 3
{ //数码管和L1扫描函数
unsigned char com[8]={0x00,0xff,0xff,0xff,0xff,0xff,0xff,0xff}; //用于控制数码管的亮灭
static char i;
TH1=(65536-2500)/256; //每2ms扫描一次
TL1=(65536-2500)%256;
P2&=0x1f;
P0=0xff;
P2|=Y7C;
P2&=0x1f;
P0=smg_we[i]&com[i];
P2|=Y6C;
P2&=0x1f;
if(i==1|i==5)
P0=smg_du[tab[i]]&0x7f; //为第二和第六个数码管加小数点
else
P0=smg_du[tab[i]];
P2|=Y7C;
P2&=0x1f;
if(flag1) //开L1
{
P2&=0x1f;
P0=0xfe;
P2=Y4C;
P2&=0x1f;
}
else //关L1
{
P2&=0x1f;
P0=0xff;
P2=Y4C;
P2&=0x1f;
}
if(i==7) //扫描完8个数码管就清零从新扫描
{
i=0;
}
else
i++;
}
复制代码
所有资料51hei提供下载:
自动售水机.zip
(517.53 KB, 下载次数: 4)
2019-5-19 10:57 上传
点击文件名下载附件
售水机
下载积分: 黑币 -5
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1