基于51单片机的US-100(超声波模块)1602显示程序
基于51单片机的US-100(超声波模块)1602显示程序
/****************************************
*************************************/
Name: LCD1602+US-100+STC89C52 HC-SR04 超声波测距模块串口程序
晶振:11.0592M Designed by : 庶野琴风
Date:2016/08/11
QQ: 397739038
接线:模块TRIG接 P3.1 ECH0 接P3.0
RS(CS) 接 P2.0;
RW(SID) 接 P2.1;
E(SCLK) 接 P2.2;
BF 接 P0.7;
/****************************************
*************************************/
#include
#include
#define nops
{_nop_();_nop_();_nop_();_nop_();}
/******************************引脚及变量
的定义****************************/
sbit RS = P2^0; //寄存器选择位
sbit RW = P2^1; //读取选择位
sbit E = P2^2; //使能信号位
sbit BF = P0^7; //忙碌信号位
unsigned char code Tab[] = {"0123456789"}; unsigned char code string[] = {"range:2cm--4.5m"};
char part,ge,shi,bai;
char idata GLengthLoh[2]; //接收缓冲区
bit success_flag; //定义测试成功标志
位
/****************************************
*****************/
/*********函数名称:delay1ms(void) ******************/
/*********函数功能:延时1毫秒
******************/
/*********函数参数:void ******************/
/****************************************
*****************/
void delay1ms(void) //误差
-0.651041666667us
{
char a,b;
for(b=102;b>0;b--)
for(a=3;a>0;a--);
}
/****************************************
*****************/
/*********函数名称:delaynms(char n)
******************/
/*********函数功能:延时n个1毫秒
******************/
/*********函数参数:n ******************/
/****************************************
*****************/
void delaynms(char n)
{
char a;
for(a = 0;a > n;a--)
delay1ms();
}
/****************************************
*****************/
/*********函数名称:BusyTest(void) ******************/
/*********函数功能:判断液晶模块忙碌状态
******************/
/*********函数参数:返回值:result
******************/
/****************************************
*****************/
unsigned char BusyTest()
{
bit result;
RS = 0;
RW = 1; //RS为低电平,RW为高电平时,
可以读状态
E = 1; //使能为高电平时可读取信息
nops; //延时40us,给硬件反应时间
result = BF; //将忙碌标志位电平赋给
result
E = 0; //使能1到0:执行指令
return result;
}
/****************************************
*****************/
/*********函数名称:WriteInstruction(char dictate)*******/
/*********函数功能:将模式设置指令或显示地
址写入液晶模块**/
/*********函数参数:dictate ******************/
/****************************************
*****************/
void WriteInstruction(char dictate)
{
while(BusyTest() == 1); //如果忙碌标
志位忙碌则等待
RS = 0;
RW = 0; //RS/RW位同时为低电平时
可写入指令
E = 0; //使能0到1:写入指令
nops;
P0 = dictate; //将数据送入P0口,
写入数据或地址
nops;
E = 1; //使能0到1:写入指令
nops;
E = 0; //使能1到0:执行指令
}
/****************************************
*****************/
/*********函数名称:WriteAddress(char x) *******/
/*********函数功能:指定字符显示的实际地址
***********/
/*********函数参数:x ******************/
/****************************************
*****************/
void WriteAddress(char x)
{
WriteInstruction(x|0x80); //80H+地址码
}
/****************************************
*****************/
/*********函数名称:WriteData(char y) *******/
/*********函数功能:将数据(字符的标准ASCII
码)写入液晶模块*/
/*********函数参数:y ******************/
/****************************************
*****************/
void WriteData(char y)
{
while(BusyTest() == 1); //如果忙碌标
志位忙碌则等待
RS = 1;
RW = 0; //RS为高电平,RW为低电
平时,可以写入数据
E = 0;
P0 = y;
nops;
E = 1;
nops;
E = 0;
}
/****************************************
*****************/
/*********函数名称:LCDInit(void) *******/
/*********函数功能:液晶模块初始化
****************/
/*********函数参数:void ******************/
/****************************************
*****************/
void LCDInit(void)
{
delaynms(15); //延时15毫秒,首次写
入液晶指令应给反应时间
WriteInstruction(0x38); //显示模式设
置:16×2显示,5×7点阵,8位数据接口
delaynms(5); //延时5秒,反应时间
WriteInstruction(0x38);
delaynms(5); //延时5秒,反应时间
WriteInstruction(0x38);
delaynms(5); //连续三次,确保初始
化成功
WriteInstruction(0x0c); //显示模式设
置:显示开,无光标,光标不闪烁
delaynms(5);
WriteInstruction(0x06);//显示模式设
置:显示光标右移,屏幕不移动
delaynms(5);
WriteInstruction(0x01); //清屏
delaynms(5);
}
/****************************************
*****************/
/*********函数名称:UART_Send(char dat) *******/
/*********函数功能:串口发送函数
****************/
/*********函数参数:dat ******************/
/****************************************
*****************/
void UART_Send(char dat)
{
TI = 0; // 清发送标志
SBUF = dat; //如果TI为0等待
while (!TI); //等待发送数据
}
/****************************************
*****************/
/*********函数名称:UART_Init() ***************/
/*********函数功能:串口初始化函数
****************/
/*********函数参数:无
******************/
/****************************************
*****************/
void UART_Init()
{
TH1 = 0xFD;
TL1 = 0xFD;
TMOD = 0x21; //设置定时器1
为模式2;定时器0为模式1
TH0 =(65536-2500)/256; //约2.50MS定
时器初值
TL0 =(65536-2500)%256; //约2.50MS定
时器初值
ET0 = 1;
TR0 = 1; //启动定时器
TR1 = 1; //启动定时器
SM0 SM1
SM0 = 0; //串口通信模式
设置 0 0 = 0
SM1 = 1; // 0 1 = 1
// 1 0 = 2
// 1 1 = 3
REN = 1; //串口允许接收数据
ES = 1; //开串中断
EA = 1;
}
/****************************************
*****************/
/*********函数名称:UART_ISR(void) ***************/
/*********函数功能:串口中断函数
****************/
/*********函数参数:void ******************/
/****************************************
*****************/
void UART_ISR(void) interrupt 4
{
char temp,k;
ES = 0; //关中断
if(RI)
{
RI = 0; //清接收标志
temp = SBUF;
GLengthLoh[k] = temp;
k++;
if(k == 2) //k=数据长度
k = 0;
}
ES = 1; //开中断
}
/****************************************
*****************/
/*********函数名称:timer0() ***************/
/*********函数功能:定时器函数
****************/
/*********函数参数:void ******************/
/****************************************
*****************/
timer0() interrupt 1 // 定时器0中
断是1号
{
TH0 =(65536-2500)/256; //约2.50MS定时
器初值
TL0 =(65536-2500)%256; //约2.50MS定时
器初值 TH0 = 0xef; TL0 = 0x94; //
写入定时器0初始值
}
/****************************************
*****************/
/*********函数名称:conversion(int8
temp_data) *******/
/*********函数功能:数据转换
****************/
/*********函数参数:temp_data ******************/
/****************************************
*****************/
void conversion(int temp_data)
{
char
part_data,ge_data,shi_data,bai_data;
bai_data = temp_data / 1000;
shi_data = (temp_data % 1000) / 100;
ge_data = (temp_data % 100) / 10;
part_data = temp_data % 10;
EA = 0;
bai = bai_data;
shi = shi_data;
ge = ge_data;
part = part_data;
EA = 1;
}
/****************************************
*****************/
/*********函数名称:main(void)
*******/
/*********函数功能:主函数
****************/
/*********函数参数:void ******************/
/****************************************
*****************/
void main(void)
{
int k;
long PreLength;
LCDInit(); //调用液晶初始化
函数
delaynms(10);
UART_Init();
PreLength = 0;
k = 0;
while(1)
{
WriteAddress(0x01);
while(string[k] != '\0')
{
WriteData(string[k]);
k++;
}
UART_Send(0X55);
PreLength = GLengthLoh[0] * 256 + GLengthLoh[1] - 5;
conversion(PreLength);
WriteAddress(0x41); //从第2行第6列开始显示
WriteData('J'); //将特定的字符常量写入LCD
WriteData('U');
WriteData('L');
WriteData('I');
WriteData(':');
if(PreLength <= 4500 && PreLength >=
20)
{
WriteData(Tab[bai]); //将百位数字的字符常量写入LCD
WriteData(Tab[shi]); //将十位数字的字符常量写入LCD
WriteData(Tab[ge]); //将个位数字的字符常量写入LCD
WriteData('.');
WriteData(Tab[part]);
}
else
{
WriteData('-');
WriteData('-');
WriteData('-');
WriteData('-');
WriteData('-');
}
WriteData(' ');
WriteData('c');
WriteData('m');
} }