基于STC8H8K64U单片机和DS18B20实现温度的串口通信读取
创作时间:
作者:
@小白创作中心
基于STC8H8K64U单片机和DS18B20实现温度的串口通信读取
引用
1
来源
1.
http://www.51hei.com/bbs/dpj-236658-1.html
本文介绍了一种基于STC8H8K64U单片机和DS18B20温度传感器的温度监测系统。该系统能够实时读取温度数据并通过串口发送至电脑,具有较高的实用性和技术参考价值。
功能实现和项目描述
单片机读取温度传感器数据,并通过串口发送至电脑。
电路及实现效果
单片机代码
/*--- DS18B20 ---
Function: Display temperature by UART
Board: STC8H8K64U
Main Fosc: 22.1184 MHz
Baud rate: 9600 bps
Connect: DQ --> P20
Author: Jin-Lei Li
Email: lijinlei0907@163.com
Date: June.27, 2024
Ref: UART section in STC32 series datasheet
---*/
#include "STC8H.h"
#include "intrins.h"
typedef unsigned char u8;
typedef unsigned int u16;
typedef unsigned long int u32;
#define MAIN_Fosc 22118400UL
#define Baudrate 9600
#define BRT (65536 - (MAIN_Fosc/Baudrate + 2)/4)
sbit DQ = P2^0;
/*-- UART --*/
bit busy;
u8 wptr;
u8 rptr;
u8 buffer[16];
/*---*/
bit MinusFlag; //温度正负 0:正数 1:负数
//u16 Temper; // temperature
void GPIO_Init();
void UartInit();
void UartSend(u8 dat);
void UartSendStr(u8 *p);
void Display();
void Delay_ms(u16 ms);
/*--- Main Program ---*/
void main(void)
{
P_SW2 |= 0x80; //扩展寄存器(XFR)访问使能
GPIO_Init();
UartInit();
ES = 1;
EA = 1;
while(1)
{
Display();
Delay_ms(500);
}
}
/*--- GPIO initialize ---*/
void GPIO_Init()
{
P0M1 = 0x00; P0M0 = 0x00;
P1M1 = 0x00; P1M0 = 0x00;
P2M1 = 0x00; P2M0 = 0x00;
P3M1 = 0x00; P3M0 = 0x00;
P4M1 = 0x00; P4M0 = 0x00;
P5M1 = 0x00; P5M0 = 0x00;
P6M1 = 0x00; P6M0 = 0x00;
P7M1 = 0x00; P7M0 = 0x00;
}
/*--- Delay time ---*/
void Delay1us(void) //@22.1184MHz
{
u8 data i;
_nop_();
i = 5;
while (--i);
}
void Delay60us(void) //@22.1184MHz
{
u8 data i, j;
_nop_();
_nop_();
i = 2;
j = 182;
do
{
while (--j);
} while (--i);
}
void Delay480us(void) //@22.1184MHz
{
u8 data i, j;
_nop_();
i = 14;
j = 199;
do
{
while (--j);
} while (--i);
}
void Delay_ms(u16 ms)
{
u16 i;
do{
i = MAIN_Fosc / 10000;
while(--i);
}while(--ms);
}
/*--- UART Send byte ---*/
void UartSend(u8 dat)
{
while (busy);
busy = 1;
SBUF = dat;
}
/*--- UART Send string ---*/
void UartSendStr(u8 *p)
{
while (*p)
{
UartSend(*p++);
}
}
/*--- UART isr ---*/
void UartIsr() interrupt 4
{
if (TI)
{
TI = 0;
busy = 0;
}
if (RI)
{
RI = 0;
buffer[wptr++] = SBUF;
wptr &= 0x0f;
}
}
/*--- UART initial ---*/
void UartInit()
{
SCON = 0x50;
TMOD = 0x00;
TL1 = BRT;
TH1 = BRT>>8;
TR1 = 1;
AUXR = 0x40;
wptr = 0x00;
rptr = 0x00;
busy = 0;
}
/*--- Initialize DS18B20 ---*/
void Init_DS18B20(void)//初始化ds1820
{
bit flag = 1;
while( flag )
{
DQ = 0; //输出低电平
Delay480us();
DQ = 1; //输出高电平
Delay60us();
flag = DQ; //读取当前电平
Delay480us();
}
}
void DS18b20_Write_0(void) //写逻辑0码
{
DQ = 0; //输出低电平
Delay60us();
DQ = 1; //输出高电平
Delay1us();
Delay1us();
}
void DS18b20_Write_1(void) //写逻辑1码
{
DQ = 0; //输出低电平
Delay1us();
Delay1us();
DQ = 1; //输出高电平
Delay60us();
}
/*--- Read level ---*/
bit DS18b20_Read(void) //读取电平
{
bit state ;
DQ = 0; //输出低电平
Delay1us();
Delay1us();
DQ = 1; //输出低电平
Delay1us();
Delay1us();
state = DQ; //读取当前电平
Delay60us();
return state;
}
/*--- Write byte ---*/
void WriteOneChar(u8 dat)//写一个字节
{
u8 i;
for( i=0;i<8;i++ ) //循环八次
{
if( dat & 0x01 )
DS18b20_Write_1();
else
DS18b20_Write_0();
dat >>=1;
}
}
/*--- Read byte ---*/
u8 ReadOneChar(void)//读一个字节
{
u8 i = 0;
u8 dat = 0;
for (i=8;i>0;i--)
{
DQ = 0; // 给脉冲信号
dat >>= 1;
DQ = 1; // 给脉冲信号
if( DS18b20_Read() ) //如果读取到的是1,
dat |= 0x80;
}
return dat;
}
/*--- Start ---*/
void Start_Convert()
{
Init_DS18B20();
WriteOneChar(0xcc);
WriteOneChar(0x44);
}
/*--- Read Temperature ---*/
u16 Readtemp(void)
{
u8 Low = 0;
u8 High = 0;
u16 Temper = 0; // temperature
float Tt = 0;
Start_Convert();
while(!DQ); //4.等待DQ变成高电平
Init_DS18B20();
WriteOneChar(0xCC); //跳过读序号列号的操作
WriteOneChar(0xBE); //读取温度寄存器
Low = ReadOneChar(); //连续读两个字节数据 //读低8位
High = ReadOneChar(); //读高8位
if( High & 0XF8 ) //有1出现就是负数
{
MinusFlag = 1; //标志位负数
Temper = (High<<8) | Low; //将温度换算成16位
Temper = (~Temper) +1; //按位取反+1
Tt = Temper*0.0625; //得到真实十进制温度值,因为DS18B20可以精确到0.0625度,所以读回数据的最低位代表的是0.0625度
Temper = Tt*10 + 0.5; //放大十倍,以便保留一位小数,并四舍五入
}
else
{
MinusFlag = 0; //标志位正数
Temper = (High<<8) | Low; //将温度换算成16位
Tt = Temper*0.0625; //最终温度保留一位小数
Temper = Tt*10 + 0.5;
}
return Temper;
}
/*--- Display temperature ---*/
void Display()
{
u16 val;
u16 shi,ge,xiaoshu;
val = Readtemp();
shi = val/100+48;
ge = val/10%10+48;
xiaoshu = val%10+48;
if( MinusFlag==1 ) // negtive
{
UartSendStr("Temperature: ");
UartSend('-');
UartSend(shi);
UartSend(ge);
UartSend('.');
UartSend(xiaoshu);
UartSendStr("\r\n");
}
else // MinusFlag==0, positive
{
UartSendStr("Temperature: ");
UartSend(shi);
UartSend(ge);
UartSend('.');
UartSend(xiaoshu);
UartSendStr("\r\n");
}
}
热门推荐
垂直跳的物理学:力量与下蹲深度
黄金和铂金有什么区别?一文详解两种贵金属的差异
Ⅱ度烧伤如何处理
构建适合您的风险偏好的投资组合策略指南
全球首个AI圣彼得大教堂上线,40万照片毫米级3D还原文艺复兴巅峰
如何轻松打开ET文件:方法与工具详解
老旧燃气管网 “危机四伏”,可燃气体监测仪如何和护航管网安全
豆瓣评分最高的10部古装剧:墨雨云间第8,梦华录第3,第一名封神
营养素的黄金搭档:食物搭配的科学
香菊胶囊使用剂量及安全用药指南
掌握灭火器使用四步法,这些火灾逃生技巧也要记牢
黄巢攻打陈州遭遇失败是导致起义最终失败的关键因素之一
准时交货 (On-Time Delivery) 的核心、挑战与优化策略
新学期:培养自律的孩子,家长要这样做
IT运维人员必考的6本证书,助力职业发展!
2024年上海市未来产业全景图谱(附空间布局、发展现状、发展规划)
浅析黄巢起义的爆发与失败
入境游爆火之下,老外也开始面临“退税难”了
纤维素增溶新方法发表于SusMat期刊
木命适合做什么行业最佳
马斯克多次发言:我们的世界可能是虚拟的,本质上是缸中之脑
长沙民政职业技术学院
定期围产期保健是什么意思
活性炭口罩:守护你在多场景下的呼吸健康
数实融合怎么走?超30万网友线上聆听的中国纺织行业数字化转型大会给出答案!
开源大型语言模型 (LLM) 会取代闭源大语言模型吗?开源和闭源 LLM区别对比
工伤康复申请流程与注意事项
EXCEL怎么计算到今天年份
韩炳哲:在信息洪流里重寻方向和意义
系统0崛起:人工智能如何塑造人类思维新模式?