📄 lcd2.c
字号:
#include <reg52.h>
#include<stdio.h>
#include <intrins.h> //内部函数,包含_nop_()空函数指令
#define uchar unsigned char
#define uint unsigned int
sbit DQ =P2^7;
sbit RS = P2^6; // 定义LCD模块控制引脚
sbit RW = P2^5;
sbit E = P2^4;
#define DataPort P0 //定义LCD模块数据端口
#define Busy 0x80 //忙标志,D7位为1说明忙
uchar Xpos; //列方向地址指针
uchar Ypos; //行方向地址指针
//以下是短延时函数
void Delay5Ms(void) {
uint i = 5552;
while(i--);
}
//以下是读忙状态函数
// 功能:在正常读写操作之前检测LCD模块的忙状态,
//D7 = 0:LCD控制器空闲;D7 = 1:LCD控制器忙
void CheckBusy( void )
{
DataPort = 0xff; //P1口写1
RS=0; //选择指令寄存器
RW=1; //选择读模式
_nop_();
E=1; //使能LCD
_nop_();
_nop_();
while( DataPort & Busy );//若D7=1,则DataPort&Busy=1,说明忙,等待
E=0; //若D7=0,说明不忙,令E=0
}
//以下是写入IR寄存器命令函数
//功能:向LCD模块写入命令字符CMD
//若 AttribC = 1 检测忙信号,若 AttribC = 0 不检测忙信号
void WriteIR(uchar CMD,uchar AttribC)
{
if (AttribC) CheckBusy();//若AttribC =1,则检测忙信号,否则,顺序执行
RS = 0; //选择指令寄存器
RW = 0; //选择写模式
_nop_();
DataPort = CMD; //将命令送数据端口
_nop_();
E = 1; //使能LCD
_nop_();
_nop_();
E = 0; //禁止LCD
}
//以下是写入DDR寄存器函数
//功能:在当前光标位置显示一个字符
void WriteDDR( char c )
{
CheckBusy(); //检测忙信号
RS = 1; //选择数据寄存器
RW = 0; //选择写模式
_nop_();
DataPort = c; // 将显示字符送往数据口
_nop_();
E = 1; //写使能
_nop_();
_nop_();
E = 0; //禁止LCD
}
//以下是光标定位函数
void LcdPos(uchar Xpos,uchar Ypos)
{
uchar tmp; //定义tmp为指令码
Xpos&=0x0f; //16xx型液晶的范围是0~15
Ypos&=0x01; //Y的范围是0~1
tmp=Xpos;
if(Ypos==1)
tmp|=0xc0; //若Ypos为1(显示第2行),地址码+0xc0
tmp|=0x80; //若Ypos为0(显示第1行),地址码+0x80
WriteIR (tmp,0);
}
//以下是初始化函数
//功能:向LCD模块写入不同命令,完成必要的初始化过程
void LcdReset( void )
{
WriteIR( 0x38, 0); //功能设置指令,8位接口,显示2行,5×7字符
WriteIR( 0x38, 1); //设置显示模式(以后均检测忙信号)
WriteIR( 0x08, 1); //显示开关控制指令,显示关闭
WriteIR( 0x01, 1); //清屏指令,将DDRAM数据全部填入"空白"
WriteIR( 0x06, 1); //输入方式设置指令,字符不动,光标自动右移一格
WriteIR( 0x0f, 1); //显示开关控制指令,显示器开,光标开,光标闪烁
}
//以下是在指定行列显示字符函数
void WriteChar(uchar Xpos,uchar Ypos,char c)
{
LcdPos(Xpos,Ypos);
WriteDDR(c);
}
//以下是显示字符串函数
void WriteString(uchar Xpos,uchar Ypos,char s[])
{
uchar p=0;
for(;;)
{
WriteChar(Xpos,Ypos,s[p]);
p++;
if(s[p]==0)
break;
if(++Xpos>=15) //每行最多显示16个字符
{
DElay5Ms(); // LCD模块初始化
Xpos=0; //如果一行显示不完,则转到下一行或上一行的第一个字符
Ypos^=1;} //如果一行显示不完,则转到下一行或上一行显示
}
}
//以下是主函数
void Delay(unsigned int i)
{
while(i--);
}
//初始化函数
Init_DS18B20(void)
{
unsigned char x=0;
DQ = 1; //DQ复位
Delay(8); //稍做延时
DQ = 0; //单片机将DQ拉低
Delay(80); //精确延时 大于 480us
DQ = 1; //拉高总线
Delay(14);
x=DQ; //稍做延时后 如果x=0则初始化成功 x=1则初始化失败
Delay(20);
}
//读一个字节
ReadOneChar(void)
{
unsigned char i=0;
unsigned char dat = 0;
for (i=8;i>0;i--)
{
DQ = 0; // 给脉冲信号
dat>>=1;
DQ = 1; // 给脉冲信号
if(DQ)
dat|=0x80;
Delay(4);
}
return(dat);
}
//写一个字节
WriteOneChar(unsigned char dat)
{
unsigned char i=0;
for (i=8; i>0; i--)
{
DQ = 0;
DQ = dat&0x01;
Delay(5);
DQ = 1;
dat>>=1;
}
}
//读取温度
ReadTemperature(void)
{
unsigned char a=0;
unsigned char b=0;
unsigned int t=0;
float tt=0;
Init_DS18B20();
WriteOneChar(0xCC); // 跳过读序号列号的操作
WriteOneChar(0x44); // 启动温度转换
Init_DS18B20();
WriteOneChar(0xCC); //跳过读序号列号的操作
WriteOneChar(0xBE); //读取温度寄存器等(共可读9个寄存器) 前两个就是温度
a=ReadOneChar();
b=ReadOneChar();
t=b;
t<<=8;
t=t|a;
tt=t*0.0625; //将温度的高位与低位合并
t= tt*10+0.5; //对结果进行4舍5入
return(t);
}
void main()
{
float k ,t;
SCON= 0x40; //串口方式1
REN=1; //允许接收
TMOD= 0x20; //定时器1定时方式2
TH1= 0xE8; //11.0592MHz 1200波特率
TL1= 0xE6;
TI= 1;
TR1= 1;
while(1)
{
k=ReadTemperature();
t=k/10;
printf("%3f\n",t);
Delay(1000);
}
}
/*void main(void)
{
for(k=0,k<)
int s[]="!@#$%^&*()_+|[]{}";
LcdReset(); // LCD模块初始化
Delay5Ms(); //延是等待复位
WriteString(1,0,s);
LcdPos(15,1);
for(;;)
{;}
}
*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -