25 基于51单片机的温度电流电压检测系统(压力、电压、温度、电流、LCD1602)

目录

一、主要功能

二、硬件资源

三、程序编程

四、实现现象


一、主要功能

基于51单片机,通过DS18B20检测温度,滑动变阻器连接数模转换器模拟电流、电压,通过LCD1602显示,程序里设置温度阈值为40,电流阈值为60,电压阈值为100,如果超于阈值,则蜂鸣器报警。

二、硬件资源

基于KEIL5编写C++代码,PROTEUS8.15进行仿真,全部资源在页尾,提供安装包。

编辑

三、程序编程

复制代码
#include <REGX52.H>#include<intrins.h>#include<stdio.h>#include "Delay.h"#include "LCD1602.h"#define uchar unsigned char#define uint unsigned  intsbit beep = P2^5;			  //蜂鸣器引脚sbit DS=P2^4;                 //DS18B20温度传感器sbit DS1=P2^3;                 //DS18B20温度传感器sbit CS=P1^0;                 //adc0832引脚sbit CLK=P1^1;
sbit DIO=P1^2;
sbit CS1=P1^3;                 //adc0832引脚sbit CLK1=P1^4;
sbit DIO1=P1^5;
sbit CS2   =  P1^6;        //ADC0832引脚定义sbit CLK2  =  P1^7;
sbit DIO2  =  P2^6;unsigned char count;typedef unsigned char u8;typedef unsigned int  u16;static uint temp;static float ftemp = 0.0f;//温度转变uint temp;static uint temp1;static float ftemp1= 0.0f;//温度转变uint temp1;static unsigned char num;static int wdyz=40,dymax=100,dlmax=60;  //wd38static uchar u,U,R ,u1,U1,R1,u2,U2,R2;      //定义变量void tmpchange();uint tmp();void tmpchange1();uint tmp1();void beep\_warning();void Time0\_Init()          //定时器初始化{
TMOD = 0x01;           //定时器0工作在方式1    IE   = 0x82;
TH0  = 0xfe;
TL0  = 0x33;     //11.0592MZ晶振,0.5msTR0=1;                 //定时器开始EA=1;
}void Time0_Int() interrupt 1 //中断程序{
   TH0  = 0xfe;             //重新赋值
   TL0  = 0x33;
    num++;	if(num==200)
	{	    tmpchange();        //让18b20开始转换温度
	    temp = tmp();       //读取温度
	    ftemp = temp/10.0f; //转换温度
		
		  tmpchange1();        //让18b20开始转换温度
	    temp1 = tmp1();       //读取温度
	    ftemp1 = temp1/10.0f; //转换温度
		num=0;
	}
}uchar get\_AD\_Res()            //ADC0832启动读取函数 有害气体{
	uchar i, data1=0, data2=0;
	CS=0;
	
	CLK=0;DIO=1;\_nop\_();
	CLK=1;\_nop\_();
	
	CLK=0;DIO=1;\_nop\_(); 
	CLK=1;\_nop\_();
	
	CLK=0;DIO=0;\_nop\_();
	CLK=1;\_nop\_();
	
	CLK=0;DIO=1;\_nop\_(); 
	
	for(i=0; i<8; i++)
	{
		CLK=1;\_nop\_();
		CLK=0;\_nop\_();
		data1=(data1<<1)|(uchar)DIO; 
	}	
	for(i=0; i<8; i++)
	{
		data2=data2|(uchar)DIO<<i;
		CLK=1;\_nop\_();
		CLK=0;\_nop\_();
	}
	CS=1;	
	return(data1 == data2)?data1:0;
}uchar get\_AD\_Res1()            //ADC0832启动读取函数 颗粒物{
	uchar i, data1=0, data2=0;
	CS1=0;
	
	CLK1=0;DIO1=1;\_nop\_();
	CLK1=1;\_nop\_();
	
	CLK1=0;DIO1=1;\_nop\_(); 
	CLK1=1;\_nop\_();
	
	CLK1=0;DIO1=0;\_nop\_();
	CLK1=1;\_nop\_();
	
	CLK1=0;DIO1=1;\_nop\_(); 
	
	for(i=0; i<8; i++)
	{
		CLK1=1;\_nop\_();
		CLK1=0;\_nop\_();
		data1=(data1<<1)|(uchar)DIO1; 
	}	
	for(i=0; i<8; i++)
	{
		data2=data2|(uchar)DIO1<<i;
		CLK1=1;\_nop\_();
		CLK1=0;\_nop\_();
	}
	CS1=1;	
	return(data1 == data2)?data1:0;
}uchar get\_AD\_Res2()            //ADC0832启动读取函数 有害气体{
	uchar i, data1=0, data2=0;
	CS2=0;
	
	CLK2=0;DIO2=1;\_nop\_();
	CLK2=1;\_nop\_();
	
	CLK2=0;DIO2=1;\_nop\_(); 
	CLK2=1;\_nop\_();
	
	CLK2=0;DIO2=0;\_nop\_();
	CLK2=1;\_nop\_();
	
	CLK2=0;DIO2=1;\_nop\_(); 
	
	for(i=0; i<8; i++)
	{
		CLK2=1;\_nop\_();
		CLK2=0;\_nop\_();
		data1=(data1<<1)|(uchar)DIO2; 
	}	
	for(i=0; i<8; i++)
	{
		data2=data2|(uchar)DIO2<<i;
		CLK2=1;\_nop\_();
		CLK2=0;\_nop\_();
	}
	CS2=1;	
	return(data1 == data2)?data1:0;
}void dsreset(void)            //发出命令{
  uint i;
  DS=0;		              
  i=103;				   //将总线拉低480us~960us

  while(i>0)i--;
  DS=1;					   //然后拉高总线,若DS18B20做出反应会将在15us~60us后将总线拉低
  i=4;					   //15us~60us等待
  while(i>0)i--;  //while(DS);}bit tmpreadbit(void)          //读取数据{
   uint i;
   bit dat;
   DS=0;i++;          //i++ for delay
   DS=1;i++;i++;
   dat=DS;
   i=8;while(i>0)i--;   return (dat);
}uchar tmpread(void)           //读取数据{
  uchar i,j,dat;
  dat=0;  for(i=1;i<=8;i++)
  {
    j=tmpreadbit();
    dat=(j<<7)|(dat>>1);   //读出的数据最低位在最前面,这样刚好一个字节在DAT里
  }  return(dat);
}void tmpwritebyte(uchar dat)  //传输数据给DS18B20{
  uint i;
  uchar j;
  bit testb;  for(j=1;j<=8;j++)
  {
    testb=dat&0x01;
    dat=dat>>1;    if(testb)     //write 1
    {
      DS=0;
      i++;i++;
      DS=1;
      i=8;while(i>0)i--;
    }    else
    {
      DS=0;       //write 0
      i=8;while(i>0)i--;
      DS=1;
      i++;i++;
    }
  }
}void tmpchange(void)          //DS18B20开始工作{  dsreset();  Delay(1);  tmpwritebyte(0xcc);  
  tmpwritebyte(0x44);  
}					  
uint tmp()                    //获得温度{  float tt;
  uchar a,b;  dsreset();  Delay(1);  tmpwritebyte(0xcc);  tmpwritebyte(0xbe);
  a=tmpread();//低八位
  b=tmpread();//高八位
  temp=b;
  temp<<=8;             //two byte  compose a int variable
  temp=temp|a;
  tt=temp*0.0625; //算出来的是测到的温度,数值可到小数点后两位
  temp=tt*10+0.5; //为了显示温度后的小数点后一位并作出四舍五入,因为取值运算不能取小数点后的数
  return temp;
}void dsreset1(void)            //发出命令{
  uint i;
  DS1=0;		              
  i=103;				   //将总线拉低480us~960us

  while(i>0)i--;
  DS1=1;					   //然后拉高总线,若DS18B20做出反应会将在15us~60us后将总线拉低
  i=4;					   //15us~60us等待
  while(i>0)i--;  //while(DS);}bit tmpreadbit1(void)          //读取数据{
   uint i;
   bit dat;
   DS1=0;i++;          //i++ for delay
   DS1=1;i++;i++;
   dat=DS1;
   i=8;while(i>0)i--;   return (dat);
}uchar tmpread1(void)           //读取数据{
  uchar i,j,dat;
  dat=0;  for(i=1;i<=8;i++)
  {
    j=tmpreadbit1();
    dat=(j<<7)|(dat>>1);   //读出的数据最低位在最前面,这样刚好一个字节在DAT里
  }  return(dat);
}void tmpwritebyte1(uchar dat)  //传输数据给DS18B20{
  uint i;
  uchar j;
  bit testb;  for(j=1;j<=8;j++)
  {
    testb=dat&0x01;
    dat=dat>>1;    if(testb)     //write 1
    {
      DS1=0;
      i++;i++;
      DS1=1;
      i=8;while(i>0)i--;
    }    else
    {
      DS1=0;       //write 0
      i=8;while(i>0)i--;
      DS1=1;
      i++;i++;
    }
  }
}void tmpchange1(void)          //DS18B20开始工作{  dsreset1();  Delay(1);  tmpwritebyte1(0xcc);  
  tmpwritebyte1(0x44);  
}					  
uint tmp1()                    //获得温度{  float tt1;
  uchar a,b;  dsreset1();  Delay(1);  tmpwritebyte1(0xcc);  tmpwritebyte1(0xbe);
  a=tmpread1();//低八位
  b=tmpread1();//高八位
  temp1=b;
  temp1<<=8;             //two byte  compose a int variable
  temp1=temp1|a;
  tt1=temp1*0.0625; //算出来的是测到的温度,数值可到小数点后两位
  temp1=tt1*10+0.5; //为了显示温度后的小数点后一位并作出四舍五入,因为取值运算不能取小数点后的数
  return temp1;
}void beep_warning() //温度传感器蜂鸣器警报并且电机转动{	if(ftemp>=wdyz)
	{
		beep=1;			 //蜂鸣器报警
	}	
	if(R>dymax)
	{
		beep=1;			 //蜂鸣器报警
	}	
	if(R1>dlmax)
	{
		beep=1;			 //蜂鸣器报警
	}	
	if(R2>40)
	{
		beep=1;			 //蜂鸣器报警
	}	
	if(R1>dlmax)
	{
		beep=1;			 //蜂鸣器报警
	}	
	if(ftemp1 >= 80)
	{
		beep=1;
	}	if(ftemp<wdyz && R<dymax && R1<dlmax && R2<40 && ftemp1<80)
	{
	 beep=0;					//蜂鸣器报警
	}
}void main()					  //主函数{	
	beep=0;			    //蜂鸣器关掉
	LCD_Init();         //显示屏初始化
	Time0\_Init();	LCD\_ShowString(1,1,"wendu:");	LCD\_ShowString(1,9,"scp:");	LCD\_ShowString(2,1,"dy:");	LCD_ShowString(2,7,"dl:");	while(1)
	{
		u=get\_AD\_Res();
		U=(250*u)/128;     //此处将数字信号转化为模拟信号,要根据上拉电阻阻值来确定
		R=200*U/250;	    //电压
	
	  u1=get\_AD\_Res1();
		U1=(250*u1)/128;     //此处将数字信号转化为模拟信号,要根据上拉电阻阻值来确定
		R1=200*U1/250;	   //电流
		
		u2=get\_AD\_Res2();
		U2=(250*u2)/128;     //此处将数字信号转化为模拟信号,要根据上拉电阻阻值来确定
		R2=200*U2/250;	   //气压
	
	
	  LCD_ShowNum(1,7,ftemp,2); //第一行显示温度
		LCD_ShowNum(1,13,ftemp1,2); //第一行显示温度
		LCD\_ShowNum(2,4,R,3);		LCD\_ShowNum(2,10,R1,3);		LCD\_ShowNum(2,14,R2,3);	  beep\_warning(); //温度、电压、电流超出报警
	}
}

四、实现现象

具体动态效果看B站演示视频:

基于51单片机的温度电流电压检测系统(压力、电压、温度、电流、LCD1602)

全部资料(源程序、仿真文件、安装包、演示视频):

链接:https://pan.baidu.com/s/1AUrubgakYaqnGDA-KKIVqA?pwd=w4w9

提取码:w4w9

相关推荐
良许Linux27 分钟前
32岁入行STM32迟吗?
stm32·单片机·嵌入式硬件
m0_466607701 小时前
【STM32CubeMX】ST官网MCU固件库下载及安装
stm32·单片机·嵌入式硬件
Wallace Zhang5 小时前
STM32F103_Bootloader程序开发11 - 实现 App 安全跳转至 Bootloader
stm32·嵌入式硬件·安全
GodKK老神灭5 小时前
STM32 CCR寄存器
stm32·单片机·嵌入式硬件
杰克逊的日记9 天前
MCU编程
单片机·嵌入式硬件
Python小老六9 天前
单片机测ntc热敏电阻的几种方法(软件)
数据库·单片机·嵌入式硬件
HX科技10 天前
STM32给FPGA的外挂FLASH进行升级
stm32·嵌入式硬件·fpga开发·flash·fpga升级
Suagrhaha10 天前
驱动入门的进一步深入
linux·嵌入式硬件·驱动
国科安芯10 天前
基于ASP4644多通道降压技术在电力监测系统中集成应用与发展前景
嵌入式硬件·硬件架构·硬件工程
Li Zi10 天前
STM32 ADC(DMA)双缓冲采集+串口USART(DMA)直接传输12位原始数据到上位机显示并保存WAV格式音频文件 收藏住绝对实用!!!
经验分享·stm32·单片机·嵌入式硬件