当前位置: 首页 > article >正文

基于51单片机的自动清洗系统(自动洗衣机)

目录

一、主要功能

二、硬件资源

三、程序编程

四、实现现象


一、主要功能

基于AT89C52单片机,采用DS18B20温度传感器检测温度,通过LCD1602显示屏显示,并且按键
可以加减温度的上限;
点击清洗按键后,倒计时1分钟,电机正转20s,反转20s,直到倒计时结束停止,蜂鸣器报警。
点击脱水按键后,倒计时1分钟,电机正转20s,反转20s,直到倒计时结束停止,蜂鸣器报警。
然后加三个按键,分别代表进水,出水,排水,三个LED状态灯表示。
采用滑动变阻器连接ADC0832数模转换器检测水位。

二、硬件资源

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

三、程序编程

#include "reg51.h"
#include<intrins.h>
#include<stdio.h>
#include "lcd1602.h"
#include "Delay.h"
#define uchar unsigned char
#define uint unsigned int
sbit k1=P1^2;
sbit k2=P1^3;
sbit k3=P1^4;
sbit k4=P1^5;
sbit k5=P1^6;
sbit k6=P1^7;
sbit k7=P3^0;
sbit beep=P2^7;//蜂鸣器
sbit led1=P3^7;//led
sbit led2=P3^6;
sbit led3=P3^5;
sbit out1=P3^3;//电机
sbit out2=P3^4;
sbit out3=P1^0;
sbit out4=P1^1;
sbit CS=  P2^4; //ADC0832
sbit CLK= P2^5;
sbit DIO= P2^6;
sbit DS=P3^2;                 //DS18B20温度传感器

uchar time=0,mode=0,sec=0;//系统变量
uchar fen=0,miao=0,set=1;//时间
uchar miao1=0;//倒计时
uchar disp1[]="00:00";
uchar disp2[]="00s";
uchar wd[]="00";
uchar wdyz[]="00";
uchar shuiwei[]="000";
static uint u,U,R;//水位变量
static int wdmax=50;

unsigned char count;
typedef unsigned char u8;
typedef unsigned int  u16;
static uint temp;
static float ftemp = 0.0f;//温度转变
static int wdnumber;
uint temp;
static int mode1=0;

void tmpchange();
uint tmp();
void beep_warning();

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;
}

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;
}

void swpd() //水位判断
{
	if(R>100)
	{
		out3 = 1;
		out4 = 0;
	}
	else
	{
		out3 = 1;
		out4 = 1;
	}
}


void main()//主函数
{
	init_1602();//初始化LCD
	write_string(2,0,"ms:");
	write_string(2,11,"sw");
	TMOD|=0X01;
	TH0=0X3C;
	TL0=0XB0;	
	ET0=1;//打开定时器0中断允许
	EA=1;//打开总中断
	TR0=1;//打开定时器
	beep = 1;
	while(1)
	{
	   u=get_AD_Res();
		 U=(250*u)/128;    //水位
		 R=200*U/250;	   //水位转变
     swpd();//水位判断

		if(mode==0) // 停止模式
		{
			if(!k1)
			{
				wdmax++;
				while(!k1);
			}
			
			if(!k2)
			{
				wdmax--;
				while(!k2);
			}
			
			if(!k3)
			{
				init_1602();
				mode1=0;
				write_string(2,1,"qx");
			if(mode==0)
			{
				mode=1;
				fen=set;
				miao=0;
				miao1=20;
			}
				while(!k3);
			}
			
			if(!k4)
			{
				init_1602();
				mode1=0;
				write_string(2,1,"ts");
			if(mode==0)
			{
				mode=1;
				fen=set;
				miao=0;
				miao1=20;
			}
				while(!k4);
			}
			
			if(!k5)
			{
				mode1=1;
				while(!k5);
			}
			
			if(!k6)
			{
				mode1=2;
				while(!k6);
			}

			if(!k7)
			{
			  mode1=3;
				while(!k7);
			}
		}

		 switch(mode)//模式控制
		 {
		 	 case 0:
			 	out1=1;out2=1;
				led1=1;led2=1;led3=1;
				break;
			 case 1:
			 	out1=1;out2=0;
				break;
			 case 2:
			 	out1=1;out2=1;
				break;
			 case 3:
			 	out1=0;out2=1;
				break;
			 case 4:
			 	out1=1;out2=1;
		 }
		 
		 switch(mode1)
		 {
			 case 0:
				 out3 = 0;
				out4 = 0;
				led1 = 1;
				led2 = 1;
				led3 = 1;
			 break;
			 case 1:
				out3 = 1;
				out4 = 0;
				led1 = 0;
				led2 = 1;
				led3 = 1;
			  break;
			  case 2:
				out3 = 1;
				out4 = 0;
				led1 = 1;
				led2 = 0;
				led3 = 1;
			  break;
				case 3:
				out3 = 1;
				out4 = 0;
				led1 = 1;
				led2 = 1;
				led3 = 0;
			  break;
		 }
	}
}
//定时器中断
void Timer0() interrupt 1
{
	if(time<10)//0.5s
		time++;
	else
	{
		 tmpchange();        //让18b20开始转换温度
	    temp = tmp();       //读取温度
	    ftemp = temp/10.0f; //转换温度
		  wdnumber = ftemp;
		  
		
		time=0;
		//显示
		if(mode==0)
		{
			write_string(1,0,"wd:");
			write_string(1,7,"yz:");
			wd[0]=wdnumber/10+0x30;
			wd[1]=wdnumber%10+0x30;
			
			wdyz[0]=wdmax/10+0x30;
			wdyz[1]=wdmax%10+0x30;
			
			if(wdnumber > wdmax)
			{
				beep = 0;
			}
			else
			{
				beep = 1;
			}
			
			
			write_string(1,3,wd);
			write_string(1,10,wdyz);
			
			disp1[0]=set/10+0x30;
			disp1[1]=set%10+0x30;
			disp1[3]='0';
			disp1[4]='0';
			write_string(2,5,disp1);

     	shuiwei[0]=R/100+0x30;
		  shuiwei[1]=(R%100)/10+0x30;
	   	shuiwei[2]=R%10+0x30;
		  write_string(2,13,shuiwei);
		}
		else//运行倒计时
		{
			write_string(1,0,"run:");
			disp1[0]=fen/10+0x30;
			disp1[1]=fen%10+0x30;
			disp1[3]=miao/10+0x30;
			disp1[4]=miao%10+0x30;
			write_string(2,5,disp1);
			disp2[0]=miao1/10+0x30;
			disp2[1]=miao1%10+0x30;
			write_string(1,6,disp2);

     	shuiwei[0]=R/100+0x30;
		shuiwei[1]=(R%100)/10+0x30;
	   	shuiwei[2]=R%10+0x30;
		 write_string(2,13,shuiwei);
		}
	}
	if(mode>0)
	{
	if(sec<19)//1s
		sec++;
	else
	{
		sec=0;
		if(miao>0)//秒计时
			miao--;
		else
		{
			if(fen>0)
			{
				miao=59;//分计时
				fen--;
			}
			else
			{
				beep=0;	//结束
				mode=0;
				beep=1;
			}
		}
		if(mode==1)//正转
		{
			if(miao1>0)
			 	miao1--;
			else
			{
				miao1=20;
				mode=3;
			}
		}
		else if(mode==2)//暂停
		{
			if(miao1>0)
			 	miao1--;
			else
			{
				miao1=25;
				mode=3;
			}
		}
		else if(mode==3)//反转
		{
			if(miao1>0)
			 	miao1--;
			else
			{
				miao1=20;
				mode=1;
			}
		}
		else if(mode==4)//暂停
		{
			if(miao1>0)
			 	miao1--;
			else
			{
				miao1=20;
				mode=1;
			}
		}	
		else
		{
			miao1=0;
				init_1602();
			beep = 0;
			Delay(500);
			beep = 1;
		}			
	}
	}
	TH0=0X3C;
	TL0=0XB0;
}

四、实现现象

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

基于51单片机的自动清洗系统(自动洗衣机)


全部资料(源程序、仿真文件、安装包、演示视频):
链接:https://pan.baidu.com/s/1ddJ3RP7JqBRiUF7uI6a2tw?pwd=ahdy 
提取码:ahdy 


http://www.kler.cn/a/310783.html

相关文章:

  • Java Stream 流常用操作大全
  • Python教程笔记(1)
  • git命令及原理
  • 计算机网络常见面试题(一):TCP/IP五层模型、TCP三次握手、四次挥手,TCP传输可靠性保障、ARQ协议
  • 24/11/11 算法笔记 泊松融合
  • C++实现用户分组--学习
  • 【QT】系统-上
  • ​补​充​元​象​二​面​
  • Hexo框架学习——从安装到配置
  • SpringBoot:解析excel
  • PowerBI 关于FILTERS函数和VALUES函数
  • Spring模块详解Ⅳ(Spring ORM和Spring Transaction)
  • RedisTemplate混用带来的序列化问题
  • json.dumps 中的参数
  • 预警提醒并生成日志,便于后期追溯的智慧地产开源了
  • 让IT部门弄一个炫酷的数字驾驶舱就是数字化转型成功?
  • Vue 3 中动态赋值 ref 的应用
  • windows下使用 vscode 远程X11服务GUI显示的三种方法
  • 从种草到销售:家居品牌构建O2O私域运营的完整闭环
  • 考研数学精解【3】
  • 四、(JS)JS中常见的加载事件
  • 软考(中级-软件设计师)(0919)
  • 百度Android IM SDK组件能力建设及应用
  • Golang、Python、C语言、Java的圆桌会议
  • https和http区别
  • 【网络】TCP/IP 五层网络模型:网络层