基于单片机的角度、水位、温度、辅助热源、电机仿真

目录

一、主要功能

二、硬件资源

三、程序编程

四、实现现象


一、主要功能

基于51单片机
采用滑动变阻器连接ADC0832数模转换器模拟角度传感器,水位传感器;
采样DS18B20温度传感器检测温度

通过LCD1602显示,第一行显示温度、水位、角度、指定温度
两个按键负责L298N驱动电机的正反转:
按键按下不动,电机正转,松开停止;第二个按键按下,电机反转,松开停止

辅助热源按键,按下后,对应的LED灯亮起,此时两个按键负责辅热温度的增减,一次调整10度
温度超过阈值,蜂鸣器启动;

手动上水按键可以启动进水阀继电器和通气阀继电器;

自动上水通过水位判断:水位低于阈值后,辅热对应的LED灯关掉,进水阀和通气阀打开;
水位高于阈值后,打开排水阀和通气阀;

然后如果加热到达阈值和水位到达阈值,蜂鸣器报警2秒。

二、硬件资源

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

三、程序编程

cpp 复制代码
#include "public.h"
#include <intrins.h>		//定义头文件
#include <stdio.h>		//定义头文件
#include "lcd1602.h"
#include "ds18b20.h"
#include "stdio.h"
#include "i2c.h"
#define uchar unsigned char	 //定义变量
#define uint unsigned  int	 //定义变量
	
char buff[15];
char buff1[3];
	
unsigned char readTem = 0 ;//定义读时间标志
unsigned char readADCFlag = 0 ;	  //读取标志
unsigned long time_20ms=0;		   //定时器计数

sbit IN1 = P1^0; //进水阀
sbit IN2 = P1^1;//排水阀
sbit KEY1=P1^2;
sbit KEY2=P1^3;
sbit KEY3=P1^4;
sbit KEY4=P2^2;
sbit IN3=P1^5;  //通气阀
sbit IN4=P1^6;  //LED灯
sbit beep=P1^7;
sbit key5=P3^3;
sbit key6=P3^4;
sbit out1=P3^5;
sbit out2=P3^6;

sbit CS=P3^0;                 //adc0832引脚
sbit CLK=P3^1;				  //adc0832引脚
sbit DIO=P3^2;				  //adc0832引脚

void Init_Timer0(void);	   //函数声明
float Lv=0.0;		  	//光照采集电压
float Lval =0;		 //光照值
static int sdflag=0;
float u;

uchar get_AD_Res()            //ADC0832启动读取函数
{
	uchar i, data1=0, data2=0;	 //赋值变量
	CS=0;						 //CS赋值低电平
	
	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;	//返回值
}
/*******************************************************************************
* 函 数 名       : main
* 函数功能		 : 主函数
* 输    入       : 无
* 输    出    	 : 无
*******************************************************************************/
void main()
{	
	u8 i=0;
	int temp_yz=60;
  float temp_value;
	char temp_buf[16];
	int flag=0;
	int one=0;
	unsigned char midval;  
	ds18b20_init();//初始化DS18B20
	Init_Timer0();
	lcd1602_init();
	 out1 = 0;
		 out2 = 0;
	while(1)
	{
			u=get_AD_Res();	       //读取ADC0832值
		if(u>80)
		{
			u=80;
		}
		else if(u<10)
		{
			u=10;
		}
		
		temp_value=ds18b20_read_temperture();//保留温度值小数后一位
		if(KEY2==0)
		{
			delay_ms(20);
			{
				if(KEY2==0)
				{
					temp_yz=temp_yz+10;
					while(KEY2==0);
				}
			}
		}
		if(KEY3==0)
		{
			delay_ms(20);
			{
				if(KEY3==0)
				{
					temp_yz=temp_yz-10;
					while(KEY3==0);
				}
			}
		}
		if(KEY1)
		{
			IN4=1; //控制LED灯
		}
		
		if(KEY4==0)
		{
			sdflag++;
			if(sdflag>1)
			{
				sdflag = 0;
			}
			while(KEY4==0);
		}
		
   if(key5)
	 {
		 out1 = 0;
	 }
	 else
	 {
		 out1 = 1;
	 }
	if(key6)
	{
		out2 = 0;
	}		
	else
	{
		out2 =1;
	}

		
  
		if(temp_value<0)//负温度
		{
			temp_value=-temp_value;
			
		}else if(temp_value>0&&temp_value<100)
		{
			sprintf(temp_buf,"Temp:%2.1f C   %d",temp_value,temp_yz);
			lcd1602_show_string(0,0,temp_buf);
			if(KEY1==0)
			{
				if(temp_value<temp_yz&&Lval>10)
				{
					flag=0;
					IN4=0;
				}else if(Lval<10||temp_value>=temp_yz)
				{
					IN4=1;
				}
				
				if(temp_value==temp_yz && Lval==80)
				{
					if(flag==0)
					{
						beep=0;
						IN4=1;
						delay_ms(2000);
						beep=1;
						flag=1;
					}
				}

				
			}
		}
		
	
		if(readADCFlag == 1)		//定时读取adc
		{
			midval=ReadADC(3);		//转换的结果,在下次,才能读出
			Lv=(float)midval/255.0*5.0;		
			Lval = Lv*20;
			delay_ms(10);          //延时有助于稳定
			sprintf(buff,"SW:%3.2fCM  %f",Lval,u);//打印电压电流值
			lcd1602_show_string(0,1,buff);//显示
			if(Lval<10) //液位小于10
			{
				one=0;   
				IN1=IN3=0; //打开进水阀和通气阀
			}
			else if(Lval>=80)
			{
				one = 1;
			}
			if(one==1)
			{
				if(sdflag == 0)
				{
					IN1=1;
					IN2=0;
					IN3=0;
				}
				if(sdflag == 1)
				{
					IN1=0;
					IN2=0;
					IN3=0;
				}
			}
			else if(one == 0)
			{
				if(KEY4==1)
				IN2=1;
			}
			readADCFlag = 0 ;
	 }
		delay_ms(1);		
	}
}



void Init_Timer0(void)
{
	TMOD |= 0x01;	  //使用模式1,16位定时器,使用"|"符号可以在使用多个定时器时不受影响		     
	TH0=(65536-20000)/256;		  //重新赋值 20ms
	TL0=(65536-20000)%256;
	EA=1;            //总中断打开
	ET0=1;           //定时器中断打开
	TR0=1;           //定时器开关打开
}

void Timer0_isr(void) interrupt 1 
{
	TH0=(65536-20000)/256;		  //重新赋值 20ms
	TL0=(65536-20000)%256;
	
	time_20ms++;
	if(time_20ms % 20 == 0)	//定时读取adc采集
	{
	 	readADCFlag = 1;
	}
	if(time_20ms % 40 == 0)		//定时读取温度
	{
	 	readTem = 1;	 //读取温度	标志
	}
}

四、实现现象

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

基于单片机的角度、水位、温度、辅助热源、电机仿真

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

百度网盘下载资料https://pan.baidu.com/s/1CHGuhkCkXYeMc5NHkZt8jg?pwd=an2x

相关推荐
哦豁灬3 小时前
树莓派pico上手
单片机·嵌入式硬件·micropython·树莓派pico
boldht5 小时前
嵌入式项目:STM32平衡车详解 (基础知识篇) (基于STM32F103C8T6)
c语言·stm32·单片机·嵌入式硬件·嵌入式项目·单片机平衡小车
夜间去看海6 小时前
基于单片机的小车行走加温湿度检测系统
单片机·嵌入式硬件·proteus
白天看花7 小时前
25 基于51单片机的温度电流电压检测系统(压力、电压、温度、电流、LCD1602)
单片机·嵌入式硬件·51单片机
辰哥单片机设计8 小时前
有源蜂鸣器(5V STM32)
stm32·单片机·嵌入式硬件·传感器
逢生博客9 小时前
使用电子模拟器 Wokwi 运行 ESP32 示例(Arduino IDE、VSCode、ESP32C3)
c语言·嵌入式硬件·mcu
HeiLongMada15 小时前
合宙LuatOS应用,与时间相关那些事
嵌入式硬件·物联网·硬件工程
乐思智能科技有限公司1 天前
C语言贪吃蛇小游戏演示和说明
c语言·开发语言·单片机·嵌入式硬件·dsp开发