(10)DS18B20温度传感器

DS18B20是一种常见的数字温度传感器,其控制命令和数据都是以数字信号的方式输入输出,相比较于模拟温度传感器(如热敏电阻),具有功能强大、硬件简单、易扩展、抗干扰性强等特点

测温范围:-55°C 到 +125°C通信接口:1-Wire(单总线)

其它特征:可形成总线结构、内置温度报警功能、可寄生供电

(10)DS18B20温度传感器_第1张图片

(10)DS18B20温度传感器_第2张图片

(10)DS18B20温度传感器_第3张图片

通过DQ线对该器件进行通讯

单总线:

单总线(1-Wire BUS)是由Dallas公司开发的一种通用数据总线

一根通信线:DQ异步、半双工

单总线只需要一根通信线即可实现数据的双向传输,当采用寄生供电时,还可以省去设备的VDD线路,此时,供电加通信只需要DQ和GND两根线

单总线电路规范:

  • 设备的DQ均要配置成开漏输出模式
  • DQ添加一个上拉电阻,阻值一般为4.7KΩ左右(前两条原因同I2C多机通讯)
  • 若此总线的从机采取寄生供电,则主机还应配一个强上拉输出电路

不采用寄生供电:

(10)DS18B20温度传感器_第4张图片

采用寄生供电:

(10)DS18B20温度传感器_第5张图片

单总线时序结构:

(10)DS18B20温度传感器_第6张图片

(10)DS18B20温度传感器_第7张图片

(10)DS18B20温度传感器_第8张图片

(10)DS18B20温度传感器_第9张图片

ROM指令:对64 BIT ROM进行操作

功能操作:对RAM暂存器进行操作

(10)DS18B20温度传感器_第10张图片

数据帧:

(10)DS18B20温度传感器_第11张图片

(10)DS18B20温度传感器_第12张图片

sbit OneWire_DQ = P3^7;

/**
	* @brief 单总线初始化
	* @param 
	* @retval 从机应答返回0,反之返回1
	*/
unsigned char OneWire_Init(){
	unsigned char i, AckBit;
	OneWire_DQ = 1; // 初始化DQ
	OneWire_DQ = 0; // 拉低DQ
	
	i = 219; while (--i);// 主机延时481us
	
	OneWire_DQ = 1; // 主机释放总线
	
	i = 29; while (--i); // 主机延时70us,等待从机操作
	
	AckBit = OneWire_DQ;
	
	i = 219; while (--i);// 主机延时481us,等待从机释放总线
	
	return AckBit;
}


/**
	* @brief 单总线发送一位
	* @param Bit 待发送的位
	* @retval 
	*/
void OneWire_SendBit(unsigned char Bit){
	unsigned char i;
	OneWire_DQ = 0; // 拉低DQ
	
	i = 3; while (--i); // 主机延时13us
	
	OneWire_DQ = Bit; // 放入总线
	
	i = 22; while (--i); // 主机延时54us,等待从机操作
	
	OneWire_DQ = 1; // 主机释放总线
}


/**
	* @brief 单总线接收一位
	* @param 
	* @retval 接收来的位
	*/
unsigned char OneWire_ReceiveBit(){
	unsigned char i, Bit;
	OneWire_DQ = 0; // 拉低DQ
	
	i = 2; while (--i); // 延时10us
	
	OneWire_DQ = 1; // 主机释放总线
	
	i = 2; while (--i); // 延时10us,等待从机操作
	
	Bit = OneWire_DQ; // 读取总线值
	
	i = 21; while (--i); // 延时50us,等待从机释放总线
	
	return Bit;
}


/**
	* @brief 单总线发送一个字节
	* @param Byte 待发送的字节
	* @retval 
	*/
void OneWire_SendByte(unsigned char Byte){
	unsigned char i;
	for(i = 0; i < 8; i++){
		OneWire_SendBit(Byte & (0x01 << i));
	}
}


/**
	* @brief 单总线接收一个字节
	* @param 
	* @retval 接收来的字节
	*/
unsigned char OneWire_ReceiveByte(){
	unsigned char i, Byte = 0;
	for(i = 0; i < 8; i++){
		if(OneWire_ReceiveBit()){Byte |= 0x01 << i;}
	}
	return Byte;
}
//DS18B20指令
#define DS18B20_SKIP_ROM			0xCC
#define DS18B20_CONVERT_T			0x44
#define DS18B20_READ_SCRATCHPAD 	0xBE

/**
	* @brief 更新温度暂存器
	* @param 
	* @retval 
	*/
void DS18B20_ConvertT(){
	OneWire_Init();
	OneWire_SendByte(DS18B20_SKIP_ROM); // skip rom
	OneWire_SendByte(DS18B20_CONVERT_T); // 更新暂存器
}


/**
	* @brief 读取温度暂存器中的温度值
	* @param 
	* @retval 温度的浮点型
	*/
float DS18B20_ReadT(){
	unsigned char TLSB, TMSB;
	int temp;
	float T;
	
	OneWire_Init();
	OneWire_SendByte(DS18B20_SKIP_ROM); // skip rom
	OneWire_SendByte(DS18B20_READ_SCRATCHPAD); // 读取暂存器
	
	TLSB = OneWire_ReceiveByte(); // 读取
	TMSB = OneWire_ReceiveByte();
	
	temp = (TMSB << 8) | TLSB; // 组合结果,高8位和低8位
	
	T = temp / 16.0; // 低4位表示小数,所以把第5位放到个位上(二进制左移一位等效于十进制乘二)
	return T;
}

显示float:

if(t < 0){
    t = -t;
    LCD_ShowChar(1, 1, '-');
}else{
    LCD_ShowChar(1, 1, '+');
}
LCD_ShowNum(1, 2, t, 3);
LCD_ShowChar(1, 5, '.');
LCD_ShowNum(1, 6, (unsigned long)(t * 10000) % 10000, 4);
}

你可能感兴趣的:(51单片机入门,单片机,嵌入式硬件,51单片机)