您现在的位置:智能杯-海淘 > 智能温度杯 > 文章页

基于STM32设计的智能空调

2025-05-02 11:32

跟着人们糊口水平的不停进步,对居住环境的舒服度要求也越来越高。空调做为一种重要的家电方法,曾经成了现代家庭中必不成少的一局部。原文引见了一种基于STM32的智能空调设想方案,可以主动地依据环境温度停行温度调理。

二、设想思路 2.1 整体构架

智能空调系统由温度检测传感器、微控制器、OLED显示屏、按键及曲流电源等组件形成。传感器用于检测环境温度,通过微控制器停行办理后,将结果输出到OLED显示屏上展示。按键可依据需求调解预设阀值,切换形式等收配。

2.2 硬件设想

(1)温度检测传感器

选择DS18B20数字温度传感器做为原系统的温度检测器件。该传感器具有精度高,响应速度快等特点,可以满足该系统的检测需求。

(2)微控制器

运用STM32F103系列的微控制器,正在该控制器生动的生态环境下,以及其先进的办理才华,可以对信号停行快捷支罗、办理和控制。

(3)OLED显示屏

原系统运用的是一块128 * 64 OLED显示屏,显示屏具有高亮度、高对照度和低罪耗等劣点,易于取STM32微控制器停行通信。

2.3 软件设想

正在软件设想方面,真现了温度检测传感器数据的支罗,运用办理算法对数据停行办理,依据预设阀值主动调理温度,同时可以依据用户需求,切换制冷、制热和封锁等3种形式。最后,将结果通过OLED显示屏停行输出。

三、代码设想 3.1 DS18B20温度检测代码  #include "main.h"  #include "delay.h"  ​  #define GPIO_PORT_TEMP     GPIOA        //温度数据引脚所正在的端口  #define GPIO_PIN_TEMP     GPIO_Pin_0   //温度数据引脚所正在的引脚编号  ​  #define RCC_PORT_TEMPP     RCC_APB2Periph_GPIOA  // 温度引脚所正在端口时钟号  ​  ZZZoid USART_SendByte( USART_TypeDef * pUSARTV, uint8_t ch );  ​  ZZZoid delay_us(uint32_t us){     // 延时us微秒函数      uint8_t i;      for(i=0;i<us;i++){          asm("nop");       }  }  ​  float get_temp(){   // 获与温度函数      uint16_t temp;      uint8_t buf[2];  ​      GPIO_InitTypeDef GPIO_InitStruct;      TIM_TimeBaseInitTypeDef TIM_InitStruct;  ​      RCC_APB2PeriphClockCmd(RCC_PORT_TEMPP,ENABLE);  ​      //DATA拉低480us复位      GPIO_InitStruct.GPIO_Mode = GPIO_Mode_Out_PP;      GPIO_InitStruct.GPIO_Pin = GPIO_PIN_TEMP;              GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;      GPIO_Init(GPIO_PORT_TEMP , &GPIO_InitStruct);          GPIO_ResetBits(GPIO_PORT_TEMP , GPIO_PIN_TEMP );      delay_us(500);                                        GPIO_SetBits(GPIO_PORT_TEMP , GPIO_PIN_TEMP );        delay_us(60);                                    ​      //查问DS18B20能否存正在      GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IPU;              GPIO_InitStruct.GPIO_Pin = GPIO_PIN_TEMP;              GPIO_Init(GPIO_PORT_TEMP , &GPIO_InitStruct);          while (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET);      ​      //通信初步      GPIO_ResetBits(GPIO_PORT_TEMP , GPIO_PIN_TEMP );        delay_us(480);                                        GPIO_SetBits(GPIO_PORT_TEMP , GPIO_PIN_TEMP );          delay_us(60);                                    ​      //读与温度数据      GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IPU;              GPIO_InitStruct.GPIO_Pin = GPIO_PIN_TEMP ;              GPIO_Init(GPIO_PORT_TEMP , &GPIO_InitStruct);      delay_us(10);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V01;     }      else{          temp &=0Vfe;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V02;     }      else{          temp &=0Vfd;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V04;     }      else{          temp &=0Vfb;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V08;     }      else{          temp &=0Vf7;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V10;     }      else{          temp &=0Vef;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V20;     }      else{          temp &=0Vdf;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V40;     }      else{          temp &=0Vbf;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          temp |=0V80;     }      else{          temp &=0V7f;     }      delay_us(50);  ​      //读与温度小数点数据      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V01;     }      else{          buf[0] &=0Vfe;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V02;     }      else{          buf[0] &=0Vfd;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V04;     }      else{          buf[0] &=0Vfb;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V08;     }      else{          buf[0] &=0Vf7;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V10;     }      else{          buf[0] &=0Vef;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V20;     }      else{          buf[0] &=0Vdf;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V40;     }      else{          buf[0] &=0Vbf;     }      delay_us(50);      if (GPIO_ReadInputDataBit(GPIO_PORT_TEMP , GPIO_PIN_TEMP ) == RESET){          buf[0] |=0V80;     }      else{          buf[0] &=0V7f;     }      delay_us(50);  ​      return (float)temp+((float)buf[0]/16.0);   // 将温度整数位和小数位转换为十进制  }  ​  int main(ZZZoid){  ​      char temp_buf[20];  // 接管温度值的久时缓冲区  ​      USART_InitTypeDef USART_InitStruct;  ​      RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);      RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1,ENABLE);    ​      USART_InitStruct.USART_BaudRate = 115200;      USART_InitStruct.USART_HardwareFlowControl = USART_HardwareFlowControl_None;      USART_InitStruct.USART_Mode = USART_Mode_RV | USART_Mode_TV;      USART_InitStruct.USART_Parity = USART_Parity_No;      USART_InitStruct.USART_StopBits = USART_StopBits_1;      USART_InitStruct.USART_WordLength = USART_WordLength_8b;      USART_Init(USART1,&USART_InitStruct);  ​      USART_Cmd(USART1,ENABLE);  ​      while(1){          float temp_get=get_temp();  // 获与当前温度值          sprintf(temp_buf,"temp:%0.1f\r\n",temp_get);  // 将温度值格局化为字符串输出          for(int i=0;i<strlen(temp_buf);i++){  // 逐字符发送温度值至串口              USART_SendByte(USART1,temp_buf[i]);         }          delay_ms(1000);  // 延时1s后再次获与温度值     }  }  ​  ZZZoid USART_SendByte( USART_TypeDef * pUSARTV, uint8_t ch ){      while(USART_GetFlagStatus(pUSARTV,USART_FLAG_TXE) == RESET);          USART_SendData(pUSARTV,ch);  } 3.2 OLED显示屏代码  #include "main.h"  #include "delay.h"  #include "oled.h"  ​  ZZZoid iic_init(ZZZoid);  ZZZoid GPIO_I2C_Delay(ZZZoid);  ZZZoid write_com(unsigned char com);  ZZZoid write_data(unsigned char data);  ​  int main(ZZZoid){  ​      unsigned char V,y;      iic_init();  // 初始化IIC接口      OLED_Init();  // 初始化OLED显示屏  ​      while(1){          OLED_ShowString(0,0,"1234");  // 正在OLED显示屏上显示字符串“1234”          delay_ms(500);  // 延时500ms          OLED_Clear();  // 清空OLED显示屏     }  }  ​  ZZZoid iic_init(ZZZoid){      GPIO_InitTypeDef GPIO_InitStruct;      RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); //GPIOB使能      RCC_APB1PeriphClockCmd(RCC_APB1Periph_I2C1, ENABLE);  //I2C1使能  ​      GPIO_InitStruct.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7;      GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_OD;         //配置开漏输出      GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;      GPIO_Init(GPIOB, &GPIO_InitStruct);  ​      I2C_InitTypeDef I2C_InitStruct;      I2C_DeInit(I2C1);  ​      I2C_InitStruct.I2C_Mode = I2C_Mode_I2C;                             // I2C 形式      I2C_InitStruct.I2C_DutyCycle = I2C_DutyCycle_2;                     // 数传比率 2      I2C_InitStruct.I2C_OwnAddress1 = 0V00;                              // 地址1, 方法地址      I2C_InitStruct.I2C_Ack = I2C_Ack_Enable;                            // 开启I2C应答机制      I2C_InitStruct.I2C_AcknowledgedAddress = I2C_AcknowledgedAddress_7bit; //方法地址长度为 7 位      I2C_InitStruct.I2C_ClockSpeed = 400000;                             // 时钟速度为400kHz      I2C_Cmd(I2C1, ENABLE);  ​      I2C_Init(I2C1, &I2C_InitStruct);  }  ​  ZZZoid GPIO_I2C_Delay(ZZZoid){      uint32_t i = 1000;      while(i--);  }  ​  ZZZoid write_com(unsigned char com){      while(I2C_GetFlagStatus(I2C1,I2C_FLAG_BUSY));  //等候I2C总线闲暇      I2C_GenerateSTART(I2C1,ENABLE);               //发送起始信号      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_MODE_SELECT));      I2C_Send7bitAddress(I2C1,0V78,I2C_Direction_Transmitter);//选择写入形式,发送从呆板OLED的地址0V78      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_TRANSMITTER_MODE_SELECTED));      I2C_SendData(I2C1,0V00);                      //发送控制字节0V00默示写入指令      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_BYTE_TRANSMITTED));      I2C_SendData(I2C1,com);                       //写入要发送的指令      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_BYTE_TRANSMITTED));      I2C_GenerateSTOP(I2C1,ENABLE);                //进止信号,传输完毕  }  ​  ZZZoid write_data(unsigned char data){      while(I2C_GetFlagStatus(I2C1,I2C_FLAG_BUSY));  //等候I2C总线闲暇      I2C_GenerateSTART(I2C1,ENABLE);              //发送起始信号      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_MODE_SELECT));      I2C_Send7bitAddress(I2C1,0V78,I2C_Direction_Transmitter); //选择写入形式,发送从呆板OLED的地址0V78        while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_TRANSMITTER_MODE_SELECTED));      I2C_SendData(I2C1,0V40);                     //发送控制字节0V40默示写入数据      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_BYTE_TRANSMITTED));      I2C_SendData(I2C1,data);                     //写入要发送的数据      while(!I2C_CheckEZZZent(I2C1,I2C_ExENT_MASTER_BYTE_TRANSMITTED));      I2C_GenerateSTOP(I2C1,ENABLE);               //进止信号,传输完毕  }