stc12c5a60s 超声波HC-SR04测距

超声波HC-SR04测距

main.c

#include <reg52.h>
#include <stdio.h>
#include <intrins.h>
#define F_f 11059200UL
#define Baud_rate 9600UL
#define uchar unsigned char
typedef unsigned int uint;

sfr AUXR = 0x8e; //辅助寄存器
sfr BRT = 0x9c; //独立波特率发生器寄存器

uchar code smgduan[17]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,
					0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};//显示0~F的值

uchar showdata[4] = {1, 3, 5, 7};

bit flag = 1;

float distance = 0;  //保存距离

uchar str[20] = 0;
//HC-SR04管脚定义
sbit TRIGGER = P1^0;
sbit ECHO = P1^1;
//蜂鸣器管脚定义
sbit BEEP = P2^0;
sbit LED = P2^7;
//位选管脚定义
sbit ASEG = P1^2;
sbit BSEG = P1^3;
sbit CSEG = P1^4;
sbit DSEG = P1^5;

void delay(uint x)
{
	uint i;
	while(x --)
		for(i = 0;i < 100; i ++);
}

void Delay40us()		//@11.0592MHz
{
	unsigned char i;

	i = 108;
	while (--i);
}

void DigDisplay(uchar i)
{
	switch(i)
	{
		case 0: ASEG = 0; BSEG = 1; CSEG = 1; DSEG = 1;break;
		case 1: ASEG = 1; BSEG = 0; CSEG = 1; DSEG = 1;break;
		case 2: ASEG = 1; BSEG = 1; CSEG = 0; DSEG = 1;break;
		case 3: ASEG = 1; BSEG = 1; CSEG = 1; DSEG = 0;break;
		default: ASEG = 1; BSEG = 1; CSEG = 1; DSEG = 1;
	}
	P0 = showdata[i];	
}

void seg4show()
{
	uint distances = (uint)(distance * 10);
	showdata[0] = smgduan[distances / 1000];
	showdata[1] = smgduan[distances / 100 % 10];
	showdata[2] = smgduan[distances / 10 % 10] | 0x80;
	showdata[3] = smgduan[distances % 10];
}

void send_str()
{
	uchar *p = str;
	while(*p)
	{
		SBUF = *p;
		while( ! TI);
		TI = 0;
		p ++;
	}
}

void trigger()
{
	TRIGGER = 1;
	Delay40us();
	TRIGGER = 0;
}

void calc()
{
	uint t;
	t = TH0 * 256 + TL0;
	t *= 12 / 11.0592;
	distance = t * 0.017; //340m/s = 340mm/ms = 0.340mm/us = 0.034cm/us
	sprintf(str,"distance:%.2fcm\n", distance);
	send_str();
	seg4show();
	if(distance <= 5 && distance >= 2)
	{
		BEEP = 0;
		LED = 0;
		delay(300);
		BEEP = 1;
		LED = 1;
	}
	else
		delay(400);
	TH0 = 0;
	TL0 = 0;
}

void HC_SRO4_init() //T1提供波特率9600,工作方式2 T0计时,工作方式1 UART1,工作方式11
{
	AUXR &= 0x3F; //定时器时钟12T模式
	TMOD = 0x21;  //设置T1工作方式2,T0工作方式1
	SCON = 0x50; //设置UART1 工作方式1
	PCON |= 0x80; //波特率加倍
	TH1 = 0xA4; //256 - F_f / (Baud_rate * 12 * 16);
	TL1 = 0xA4; //256 - F_f / (Baud_rate * 12 * 16);
	TH0 = 0;
	TL0 = 0;
	//SCON |= 0x02; //告诉putchar()服务已经准备好发送  --> TI = 1
}

void loop()
{
	trigger();
	while(!ECHO);
	TR0 = 1; //T0开始计时
	while(ECHO && flag);
	TR0 = 0; //T0计时暂停
	calc();

}

void UART1_init()
{
	PCON &= 0x7F; //波特率不加倍
	SCON = 0x50;  //设置串行工作方式1
	AUXR &= 0xFB; //独立波特率发生器时钟12T
	BRT = 256 - F_f / (Baud_rate * 12 * 32); //设置独立波特率发生器重装值
	AUXR |= 0x11; //串口1选择独立波特率发生器为波特率发生器,并启动独立波特率发生器
}

void main()
{
	TRIGGER = 0;
	BEEP = 1;
	LED = 1;
	HC_SRO4_init();
	UART1_init();
	EA = 1; //开启总中断允许
	ET0 = 1;//定时器0中断允许
	ET1 = 1;//定时器1中断允许
	TR1 = 1; //开启定时器1
	TI = 0;
	RI = 0; 
	ES = 1; //开启串行中断

	while(1)
	{
		loop();
		flag = 1;
	}
}

void timer0_routine() interrupt 1
{
	flag = 0;
}

void timer1_routine() interrupt 3
{
	static uchar t = 0;

	DigDisplay(t/5);
	t ++;
}

void UART1_routine() interrupt 4
{
	uchar send_buf;

	if(RI)
	{
		send_buf = SBUF;
		if(send_buf == 0xaa)
		{
			send_str();
		}
		RI = 0;
	}
}

你可能感兴趣的:(stc12c5a60s)