【蓝桥杯】第六届单片机国赛(2015智能物料传送)
题目
代码参考
#include "reg52.h"
#include "iic.h"
#include "intrins.h"
typedef unsigned char uint8;
typedef unsigned int uint32;
#define LED_Channel 4
#define BEEP_DELAY_Channel 5
#define COM_Channel 6
#define SMG_Channel 7
#define ADC_Addr 0x90
#define ATC20_Addr 0xA0
#define t1addr 0x00
#define t2addr 0x02
sfr P4 = 0xc0;
sfr AUXR = 0x8e;
sbit TX = P1^0;
sbit RT = P1^1;
sbit LED3 = P0^2;
sbit LED4 = P0^3;
sbit S4 = P3^3;
sbit S5 = P3^2;
sbit S6 = P3^1;
sbit S7 = P3^0;
uint8 cnt50 = 0;//定时器0计数
uint8 cnt500 = 0;//灯闪烁
uint8 cnt500_2 = 0;//倒计时0.5s
uint32 cntT1 = 0;//定时器1计数
uint32 dis = 0;//距离
uint8 node = 0;//界面
uint8 Voltage = 0;//采集电压
uint8 state = 0;//空载,非空载,过载,运输过程(1,2,3,4)
uint8 rd1=0,rd2=0;//读取的时间数据
uint8 initime1=2,initime2=4;
uint8 count_flag=0;
uint8 start_flag=0;
uint8 em_flag = 0;
uint8 cfg_mode = 0;//S6模式
uint8 cat = 0;
uint8 time = 0;
uint8 code TAB[10] ={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90}; //0xfe,0xfd
void Delay(uint32 ms);
void InitHC138(uint8 Channel);
void Init_System(void);
void SMG_Display_Bit(uint8 pos,uint8 date);
void Display(uint8 node);
void SMG_Display_All(uint8 date);
void Display_Voltage(void);
void Key_Scan(void);
void echo(void);
void Send_Wave(void);
void Delay12us(void);
void ATC20_WR(uint8 addr,uint8 date);
void Contrl(void);
uint8 ATC20_RD(uint8 addr);
uint8 ADC_Read(void);
void Time0Init(void)
{
TMOD &= 0xf0;
TH0 = (65536 - 50000) / 256;
TL0 = (65536 - 50000) % 256;
TR0 = 0;
TF0 = 0;
ET0 = 1;
EA = 1;
}
void Timer1Init(void) //100微秒@11.0592MHz
{
TMOD &= 0x0F; //设置定时器模式
// AUXR |= 0x40; //定时器时钟1T模式
// TL1 = 0xAE; //设置定时初始值
// TH1 = 0xFB; //设置定时初始值
// TF1 = 0; //清除TF1标志
// TR1 = 1; //定时器1开始计时
}
void Time0Hander(void) interrupt 1
{
cnt50++;
if(cnt50 == 10)//50*10
{
cnt50 = 0;
cnt500++;
if(start_flag==1)
{
cnt500_2++;//0.5s加一次
if(cnt500_2%2 == 0)//1s
{
count_flag = 1;
}
}
}
}
void main(void)
{
Init_System();
Time0Init();
Timer1Init();
//写入初始时间
// ATC20_WR(t1addr,initime1);
// Delay(10);
// ATC20_WR(t2addr,initime2);
// Delay(10);
//读取时间
rd1 = ATC20_RD(t1addr);
Delay(10);
rd2 = ATC20_RD(t2addr);
Delay(10);
// state = 2;//空载
// cat = 2;
// dis = 30;
while(1)
{
// Voltage = ADC_Read();
// Display_Voltage();
if(state==0)
{
uint8 i;
for(i=0;i<3;i++)
{
Voltage = ADC_Read();
Delay(25);
}
if(Voltage<255/5)
state = 1;
else if(Voltage<255*4/5)
{
uint8 i;
state = 2;
for(i=0;i<3;i++)
{
echo();
Delay(25);
}
if(dis<=30)
cat = 1;
else
cat = 2;
node = 1;
}
else
state = 3;
}
else
{
Key_Scan();
Contrl();
}
Display(node);
}
}
void Contrl(void)
{
if(state == 1)
{
TR0 = 0;
TH0 = (65536 - 50000) / 256;
TL0 = (65536 - 50000) % 256;
InitHC138(LED_Channel);
P0 = 0xfe;
InitHC138(0);
}
else if(state == 2)
{
InitHC138(LED_Channel);
P0 = 0xfd;
if(em_flag==0)
{
// TR0 = 0;
// TH0 = (65536 - 50000) / 256;
// TL0 = (65536 - 50000) % 256;
InitHC138(BEEP_DELAY_Channel);
P0 = 0x10;//Relay = 1;
InitHC138(0);
}
else
{
TR0 = 1;
if(cnt500 >= 100)
cnt500 = 0;
InitHC138(LED_Channel);
LED4 = cnt500%2;
InitHC138(BEEP_DELAY_Channel);
P0 = 0x00;//Relay = 1;
InitHC138(0);
}
if(start_flag&&em_flag==0)
{
TR0 = 1;
if(count_flag == 1)//1s到达
{
if(time!=1)
--time;
else
{
InitHC138(LED_Channel);
P0 = 0xff;
InitHC138(BEEP_DELAY_Channel);
P0 = 0x00;//Relay = 1;
InitHC138(0);
//state = 0;
node = 0;
start_flag = 0;
}
count_flag = 0;
}
}
}
else if(state == 3)
{
TR0 = 1;
if(cnt500 >= 100)
cnt500 = 0;
InitHC138(LED_Channel);
P0 = 0xff;
LED3 = cnt500%2;
InitHC138(BEEP_DELAY_Channel);
P0 = 0x40;//beep = 1;
InitHC138(0);
}
// else if(state == 4)
// {
// TR0 = 0;
// TH0 = (65536 - 50000) / 256;
// TL0 = (65536 - 50000) % 256;
// }
}
void Key_Scan(void)
{
if(state == 2 )
{
if(S4 == 0)
{
Delay(10);
if(S4 == 0)
{
rd1 = ATC20_RD(t1addr);
rd2 = ATC20_RD(t2addr);
node = 2;//界面
switch(cat)
{
case 1:time = rd1;break;
case 2:time = rd2;break;
default:break;
}
start_flag = 1;
while(S4 == 0);
}
}
}
if(S5 == 0)
{
Delay(10);
if(S5 == 0)
{
em_flag = !em_flag;
if(em_flag==0)
{
TR0 = 0;
TH0 = (65536 - 50000) / 256;
TL0 = (65536 - 50000) % 256;
}
while(S5 == 0);
}
}
if(state == 1)//空载状态
{
if(S6 == 0)//设置
{
Delay(10);
if(S6 == 0)
{
if(cfg_mode == 0)
{
//读取时间
rd1 = ATC20_RD(t1addr);
rd2 = ATC20_RD(t2addr);
node = 3;//界面
}
cfg_mode++;
if(cfg_mode == 3)
{
//写入设置时间
ATC20_WR(t1addr,rd1);
Delay(10);
ATC20_WR(t2addr,rd2);
Delay(10);
cfg_mode = 0;
node = 0;//界面
}
while(S6 == 0);
}
}
if(S7 == 0)//调整
{
Delay(10);
if(S7 == 0)
{
if(cfg_mode==1)//1
{
rd1++;
if(rd1>10)
rd1 = 1;
}
else if(cfg_mode==2)
{
rd2++;
if(rd2>10)
rd2 = 1;
}
while(S7 == 0);
}
}
}
}
void echo(void)
{
AUXR |= 0x40; //定时器时钟1T模式
TL1 = 0x00; //设置定时初始值
TH1 = 0x00; //设置定时初始值
TF1 = 0; //清除TF1标志
Send_Wave();
TR1 = 1; //定时器1开始计时
while(RT==1&&TF1==0);
TR1 = 0;
if(TF1 == 1)
{
dis = 99;
TF1 = 0;
}
else
{
cntT1 = TH1;
cntT1 = (cntT1<<8)|TL1;
dis = cntT1*0.00154;
}
}
void Send_Wave(void)
{
uint8 i;
for(i=0;i<8;i++)
{
TX = 1;
Delay12us();
TX = 0;
Delay12us();
}
}
void Delay12us() //@11.0592MHz
{
unsigned char i;
_nop_();
_nop_();
_nop_();
i = 30;
while (--i);
}
void ATC20_WR(uint8 addr,uint8 date)
{
IIC_Start();
IIC_SendByte(ATC20_Addr);
IIC_WaitAck();
IIC_SendByte(addr);
IIC_WaitAck();
IIC_SendByte(date);
IIC_WaitAck();
IIC_Stop();
}
uint8 ATC20_RD(uint8 addr)
{
uint8 temp=0;
IIC_Start();
IIC_SendByte(ATC20_Addr);
IIC_WaitAck();
IIC_SendByte(addr);
IIC_WaitAck();
IIC_Stop();
IIC_Start();
IIC_SendByte(ATC20_Addr | 0x01);
IIC_WaitAck();
temp = IIC_RecByte();
IIC_SendAck(1);
IIC_Stop();
return temp;
}
uint8 ADC_Read(void)
{
uint8 temp=0;
IIC_Start();
IIC_SendByte(ADC_Addr);
IIC_WaitAck();
IIC_SendByte(0x03);
IIC_WaitAck();
IIC_Stop();
IIC_Start();
IIC_SendByte(ADC_Addr | 0x01);
IIC_WaitAck();
temp = IIC_RecByte();
IIC_SendAck(1);
IIC_Stop();
return temp;
}
void Delay(uint32 ms)
{
uint32 x,y;
for(x=0;x<ms;x++)
for(y=846;y>0;y--){}
}
void InitHC138(uint8 Channel)
{
switch(Channel)
{
case 4:P2 = (P2 & 0x1f) | 0x80;break;
case 5:P2 = (P2 & 0x1f) | 0xa0;break;
case 6:P2 = (P2 & 0x1f) | 0xc0;break;
case 7:P2 = (P2 & 0x1f) | 0xe0;break;
default:P2 &= 0x1f;
}
}
void Init_System(void)
{
InitHC138(BEEP_DELAY_Channel);
P0 = 0x00;
InitHC138(LED_Channel);
P0 = 0xff;
InitHC138(0);
}
void SMG_Display_Bit(uint8 pos,uint8 date)
{
InitHC138(COM_Channel);
P0 = 0x01<<pos;
InitHC138(SMG_Channel);
P0 = date;
InitHC138(0);
}
void SMG_Display_All(uint8 date)
{
InitHC138(COM_Channel);
P0 = 0xff;
InitHC138(SMG_Channel);
P0 = date;
InitHC138(0);
}
void Display_Voltage(void)
{
SMG_Display_Bit(0,TAB[Voltage/100]);
Delay(1);
SMG_Display_Bit(1,TAB[(Voltage%100)/10]);
Delay(1);
SMG_Display_Bit(2,TAB[Voltage%10]);
Delay(1);
SMG_Display_All(0xff);
Delay(1);
}
void Display(uint8 node)
{
if(node == 1)
{
SMG_Display_Bit(0,TAB[node]);
Delay(1);
SMG_Display_Bit(3,TAB[dis/10]);
Delay(1);
SMG_Display_Bit(4,TAB[dis%10]);
Delay(1);
SMG_Display_Bit(7,TAB[cat]);
Delay(1);
}
else if(node == 2)
{
SMG_Display_Bit(0,TAB[node]);
Delay(1);
SMG_Display_Bit(6,TAB[time/10]);
Delay(1);
SMG_Display_Bit(7,TAB[time%10]);
Delay(1);
}
else if(node == 3)
{
SMG_Display_Bit(0,TAB[node]);
Delay(1);
SMG_Display_Bit(3,TAB[rd1/10]);
Delay(1);
SMG_Display_Bit(4,TAB[rd1%10]);
Delay(1);
SMG_Display_Bit(6,TAB[rd2/10]);
Delay(1);
SMG_Display_Bit(7,TAB[rd2%10]);
Delay(1);
}
SMG_Display_All(0xff);
}
总结
LED灯的逻辑好像有问题也没仔细看,下次再改。