蓝桥杯之单片机学习(二十二)——模拟智能灌溉(附题目和完整代码)

简介: 蓝桥杯之单片机学习(二十二)——模拟智能灌溉(附题目和完整代码)

一、题目要求


0a2653c851af460fa595bd959398a8f1.png

二、代码展示


#include <STC15F2K60S2.h>
#include "iic.h"
#include "ds1302.h"
#define uchar unsigned char
#define uint unsigned int
//模式参数:0为自动、1为手动(默认为0)
uchar Mode_Check = 0;
//警告参数:1为打开、0为关闭(默认为1)
uchar Warning = 0;
//湿度参数
uchar shidu;
//时间数组
uchar shijian[] = {0, 30, 8, 0, 0, 0, 0};
//湿度阈值初始值
uchar shidu_yuzhi = 50;
//重置模式参数:1为开,0为退出
Reset_Check = 0;
uchar code SMG_duanma[18] = 
  {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,
   0x88,0x80,0xc6,0xc0,0x86,0x8e,
   0xbf,0x7f};//分别是0-9(对应下标),A-F,“-”,“.”
//分别是“0.-9.”
uchar code SMG_Dot_AC[10] = 
   {0X40,0X79,0X24,0X30,0X19,0X12,0X02,0X78,0X00,0X10};
//系统初始化
void Initsys();
//配置HC138
void SelectHC138(uchar channel);
//在pos位码上,显示value段码
void DisplaySMG_Bit(uchar pos, uchar value);
//数码管8位码显示
void SMG_Display();
//数码管的延时
void Delay_one_ms_SMG();
//独立按键(BTN)
void Alone_Key_S6_S4();
//按键消抖延时
void Delay_five_ms_Key();
//模式检查
void Alone_Key_Mode_Check();
//自动模式
void Mode_0();
//手动模式
void Mode_1();
//Rb2电压读取
uchar AD_read(uchar add);
//读取阈值
uchar EEPROM_read(uchar add);
//写入阈值
void EEPROM_write(uchar add, uchar dat);
//初始化时间
void Init_DS1302();
//读出时间
void Read_DS1302();
//正常数码管显示
void Mode_SMG_Display();
//EEPROM延时5ms
void Delay_five_ms_EEPROM();
//湿度阈值的显示
void Reset_shidu_yuzhi_Display();
//重置阈值模式
void Mode_Reset_shidu_yuzhi();
//自动模式下,检查阈值
void Check_shidu();
//警报功能
void Mode_1_Warning();
void main()
{
  Initsys();
  Init_DS1302();
  while(1)
  {
    Alone_Key_Mode_Check();
    if(Mode_Check == 0)
    {
      Mode_0();
    }
    else if(Mode_Check != 0)
    {
      Mode_1();
    }
  }
}
//自动模式
void Mode_0()
{
  SelectHC138(4);
  P0 = 0XFE;
  while(1)
  {
    Check_shidu();
    Alone_Key_S6_S4();
    Alone_Key_Mode_Check();
    Mode_SMG_Display();
    if(Mode_Check != 0)
    {
      break;
    }
  }
}
//自动模式下,检查阈值
void Check_shidu()
{
  Read_DS1302();
  shidu = (uchar)(AD_read(0X03) * 0.39f);
  if(shidu < shidu_yuzhi)
  {
    SelectHC138(5);
    P0 = 0X10;
  }
  else
  {
    SelectHC138(5);
    P0 = 0X00;
  }
}
//重置阈值模式
void Mode_Reset_shidu_yuzhi()
{
  if(Reset_Check != 0)
  {
    while(1)
    {
      Reset_shidu_yuzhi_Display();
      Alone_Key_S6_S4();
      if(Reset_Check == 0)
      {
        break;
      }
    }
  }
}
//手动模式
void Mode_1()
{
  SelectHC138(4);
  P0 = 0XFD;
  while(1)
  {
    Mode_1_Warning();
    Alone_Key_S6_S4();
    Alone_Key_Mode_Check();
    Mode_SMG_Display();
    if(Mode_Check == 0)
    {
      break;
    }
  }
}
//警报功能
void Mode_1_Warning()
{
  if(Warning != 0)
  {
    Read_DS1302();
    shidu = (uchar)(AD_read(0X03) * 0.39f);
    if(shidu < shidu_yuzhi)
    {
      SelectHC138(5);
      P0 = 0X40;
    }
    else
    {
      SelectHC138(5);
      P0 = 0X00;
    }
  }
}
//模式检查
void Alone_Key_Mode_Check()
{
  //S7按键
  if(P30 == 0)
  {
    Delay_five_ms_Key();
    if(P30 == 0)
    {
      Mode_Check = ~Mode_Check;
    }
    while(!P30);
  }
}
//独立按键(BTN)
void Alone_Key_S6_S4()
{
  //S6按键
  if(P31 == 0)
  {
    Delay_five_ms_Key();
    if(P31 == 0)
    {
      if(Mode_Check == 0)
      {
        Reset_Check = ~Reset_Check;
        while(!P31);
        Mode_Reset_shidu_yuzhi();
      }
      else if(Mode_Check != 0)
      {
        Warning = ~Warning;
      }
    }
    while(!P31);
  }
  //S5按键
  else if(P32 == 0)
  {
    Delay_five_ms_Key();
    if(P32 == 0)
    {
      if(Mode_Check == 0 && Reset_Check != 0)
      {
        shidu_yuzhi = shidu_yuzhi + 1;
        EEPROM_write(0X10, shidu_yuzhi);
        Delay_five_ms_EEPROM();
      }
      else if(Mode_Check != 0)
      {
        SelectHC138(5);
        P0 = 0X10;
      }
    }
    while(!P32);
  }
  //S4按键
  else if(P33 == 0)
  {
    Delay_five_ms_Key();
    if(P33 == 0)
    {
      if(Mode_Check == 0 && Reset_Check != 0)
      {
        shidu_yuzhi = shidu_yuzhi - 1;
        EEPROM_write(0X10, shidu_yuzhi);
        Delay_five_ms_EEPROM();
      }
      else if(Mode_Check != 0)
      {
        SelectHC138(5);
        P0 = 0X00;
      }
    }
    while(!P33);
  }
}
//配置HC138
void SelectHC138(uchar channel)
{
  switch(channel)
  {
    case 4:    //LED
      P2 = (P2 & 0X1F) | 0X80;
    break;
    case 5:    //蜂鸣器和继电器
      P2 = (P2 & 0X1F) | 0Xa0;
    break;
    case 6:    //位码
      P2 = (P2 & 0X1F) | 0Xc0;
    break;
    case 7:    //段码
      P2 = (P2 & 0X1F) | 0Xe0;
    break;
    case 0:    //锁住所有寄存器
      P2 = (P2 & 0X1F) | 0X00;
    break;
  }
}
//系统初始化
void Initsys()
{
  SelectHC138(5);
  P0 = 0X00;//关闭蜂鸣器和继电器
  SelectHC138(4);
  P0 = 0XFF;//关闭LED
  SelectHC138(6);
  P0 = 0XFF; //选择所有数码管
  SelectHC138(7);
  P0 = 0XFF; //关闭所有数码管
  EEPROM_write(0X10, shidu_yuzhi);
  Delay_five_ms_EEPROM();
}
//在pos位码上,显示value段码
void DisplaySMG_Bit(uchar pos, uchar value)
{
  SelectHC138(6);
  P0 = 0X01 << pos;
  SelectHC138(7);
  P0 = value;
}
//数码管的延时
void Delay_one_ms_SMG()
{
  uint j;
  for(j = 845; j > 0; j--);
}
//按键消抖延时
void Delay_five_ms_Key()
{
  uint i,j;
  for(i = 0; i < 5; i++)
    for(j = 845; j > 0; j--);
}
//EEPROM延时5ms
void Delay_five_ms_EEPROM()
{
  uint i,j;
  for(i = 0; i < 5; i++)
    for(j = 845; j > 0; j--);
}
//时间初始化
void Init_DS1302()
{
  uchar i, add;
  add = 0X80;  //写
  Write_Ds1302(0X8e, 0X00);
  for(i = 0; i < 7; i++)
  {
    Write_Ds1302(add, shijian[i]);
    add = add + 2;
  }
  Write_Ds1302(0X8e, 0X80);
}
//读出时间
void Read_DS1302()
{
  uchar i, add;
  add = 0X81;  //读
  Write_Ds1302(0X8e, 0X00);
  for(i = 0; i < 7; i++)
  {
    shijian[i] = Read_Ds1302(add);
    add = add + 2;
  }
  Write_Ds1302(0X8e, 0X80);
}
//读取湿度
uchar AD_read(uchar add)
{
  uchar temp;
  IIC_Start();
  IIC_SendByte(0X90);
  IIC_WaitAck();
  IIC_SendByte(add);
  IIC_WaitAck();
  IIC_Stop();
  IIC_Start();
  IIC_SendByte(0X91);
  IIC_WaitAck();
  temp = IIC_RecByte();
  IIC_Stop();
  return temp;
}
//读取阈值
uchar EEPROM_read(uchar add)
{
  uchar temp;
  IIC_Start();
  IIC_SendByte(0XA0);
  IIC_WaitAck();
  IIC_SendByte(add);
  IIC_WaitAck();
  IIC_Stop();
  IIC_Start();
  IIC_SendByte(0XA1);
  IIC_WaitAck();
  temp = IIC_RecByte();
  IIC_Stop();
  return temp;
}
//写入阈值
void EEPROM_write(uchar add, uchar dat)
{
  IIC_Start();
  IIC_SendByte(0XA0);
  IIC_WaitAck();
  IIC_SendByte(add);
  IIC_WaitAck();
  IIC_SendByte(dat);
  IIC_WaitAck();
  IIC_Stop();
}
//正常数码管显示
void Mode_SMG_Display()
{
  Read_DS1302();
  shidu = (uchar)(AD_read(0X03) * 0.39f);
  DisplaySMG_Bit(0, SMG_duanma[shijian[2] / 10]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(1, SMG_duanma[shijian[2] % 10]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(2, SMG_duanma[16]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(3, SMG_duanma[shijian[1] / 10]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(4, SMG_duanma[shijian[1] % 10]);
  Delay_one_ms_SMG();
//  DisplaySMG_Bit(5, SMG_duanma[5]);
//  Delay_one_ms_SMG();
  DisplaySMG_Bit(6, SMG_duanma[shidu / 10]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(7, SMG_duanma[shidu % 10]);
  Delay_one_ms_SMG();
  P0 = 0XFF;
}
//湿度阈值的显示
void Reset_shidu_yuzhi_Display()
{
  shidu_yuzhi = EEPROM_read(0X10);
  DisplaySMG_Bit(0, SMG_duanma[16]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(1, SMG_duanma[16]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(6, SMG_duanma[shidu_yuzhi / 10]);
  Delay_one_ms_SMG();
  DisplaySMG_Bit(7, SMG_duanma[shidu_yuzhi % 10]);
  Delay_one_ms_SMG();
}
相关文章
|
7月前
|
传感器 Web App开发 编解码
基于51单片机的智能热水器设计
基于51单片机的智能热水器设计
170 0
|
7月前
|
传感器 设计模式 监控
基于51单片机的智能婴儿看护床设计
基于51单片机的智能婴儿看护床设计
176 0
|
9月前
|
C语言
【51单片机】LCD1602显示字符串,时间、时间+按键校准、秒表计时的功能代码。
【51单片机】LCD1602显示字符串,时间、时间+按键校准、秒表计时的功能代码。
174 3
|
9月前
|
C语言
51单片机汇编语言流水灯代码
51单片机汇编语言流水灯代码
215 1
|
11月前
|
物联网 Linux 芯片
学习嵌入式是选择单片机还是Linux?
单片机通常指的是一种集成了处理器、存储器和各种外设接口的微控制器芯片,常见的有STC、51系列、AVR、ARM Cortex-M等。单片机具有低成本、低功耗、实时性强等特点,适用于对资源要求较低、功耗要求较低、实时性要求较高的嵌入式系统。学习单片机开发可以让您深入了解嵌入式系统的底层原理和硬件编程,对于对嵌入式系统底层开发感兴趣的人来说,是一个很好的选择。
230 4
|
10月前
蓝桥杯之单片机学习(终)——关于之前文章的错误及更正(附:第十四届蓝桥杯单片机赛题)
蓝桥杯之单片机学习(终)——关于之前文章的错误及更正(附:第十四届蓝桥杯单片机赛题)
226 0
|
人工智能 算法 Java
第十四届蓝桥杯集训——练习解题阶段(无序阶段)-ALGO-1005 数字游戏
第十四届蓝桥杯集训——练习解题阶段(无序阶段)-ALGO-1005 数字游戏
155 0
|
Java C语言 C++
第十四届蓝桥杯集训——练习解题阶段(无序阶段)-ALGO-1000 kAc给糖果你吃
第十四届蓝桥杯集训——练习解题阶段(无序阶段)-ALGO-1000 kAc给糖果你吃
118 0