文章目录
一、水库预警系统
1.题目要求
基于STM32F103C8单片机做一个水库预警系统,有以下传感器:步进电机(代表阀门的开关),雨量传感器 ,水流速传感器 ,压力传感器(测水压),风速传感器(测风速)等等,OLED显示屏显示传感器的内容,显示水位水质这些。蜂鸣器高水位报警,电机阀门水位高的时候打开,低水位不报警,水位设定值从0mm到1000mm。蜂鸣器响的时候灯亮,水泵在仿真运行之后开始运行就行。
2.思路
2.1 OLED显示汉字
OLED要显示中文,这需要用到取模软件,如下所示:
参数设置如下:
2.2 水质传感器等等
Proteus仿真里面没有这些传感器,统一用滑动变阻器来模拟,再通过STM32的ADC去采集,如果是采用的51单片机,内部没有集成ADC,可以通过PCF8591这种ADAC模块进行采集。
2.3 步进电机
这里采用ULN2003来驱动步进电机。
这里简单介绍下ULN2003驱动芯片。
ULN2003是一个单片高电压(最高可达50V)、高电流(单个额定输出500mA)的达林顿晶体管阵列集成电路。 它是由7对NPN达林顿晶体管组成的,它的高电压输出特性和阴极钳位二极管可以转换感应负载。单个达林顿晶体管对的集电极电流为500mA,达林顿管并联可以承受更大的电流。
ULN2003可以作为继电器驱动器,字锤驱动器、灯驱动器、显示驱动器(LED气体放电),线路驱动器和逻辑缓冲器。ULN2003的每一对达林顿晶体管的基极都有一个2.7k的串联电阻,可以直接和TTL或者5V的CMOS装置连接。它实际上就是一个功率放大器,输出端具有较大的驱动能力(电流较大)。
2.4 驱动水泵
水泵的驱动则是NPN驱动继电器的电路,当PUMP为低电平时,继电器不闭合,水泵不工作,当PUMP为高电平时,继电器闭合,水泵工作。
3.仿真图
3.1 未仿真时
3.2 开始仿真,OLED开始显示
由于OLED显示的界面有限,所以这里做了两个界面进行切换,仿真开启,水泵也开始工作,用于模拟水库。
界面1显示:水位,水质,水位阈值
界面2显示:雨量,流速,水压,风速
3.3 提高水位,开启阀门和预警
3.4 通过按键增大水位阈值,取消报警
4.仿真程序
4.1 程序说明
主控芯片:STM32F103C8
HICK:64MHZ
Systick: 1ms
串口(Uart1):9600(PA9:tx1,PA10:rx1)
OLED显示屏:SCL(PB10),SDA(PB11)、
LED模块:LED(PA7)
水位模块:ADC1(PA0)
水质模块:ADC2(PA1)
雨量传感器:ADC3(PA2)
水流速传感器:ADC4(PA3)
压力模块:ADC5(PA4)
风速模块:ADC6(PA5)
水泵:PUMP(PB2)
KEY按键:
KEY1(PB0)
KEY2(PB1)
MOTOR电机:
IN1(PB4)
IN2(PB5)
IN3(PB6)
IN4(PB7)
4.2 主函数
/* Includes ------------------------------------------------------------------*/
#include "Drv_UserSystem.h"
/**
* @brief main function.
* @param none
* @retval none
*/
int main(void)
{
UserSystemInit();//用户配置初始化
while (1)
{
if (stSysTime.flg._10ms + TEN_MILLISECOND < Time_millis()) //10ms
{
stSysTime.flg._10ms = Time_millis();
Key_Scan();//按键扫描
Warning_function();//预警函数
}
if (stSysTime.flg._50ms + FIFTY_MILLISECOND < Time_millis()) //50ms
{
stSysTime.flg._50ms = Time_millis();
ADC_Scan(); //ADC扫描
OLED_Handel();//OLED显示
}
if (stSysTime.flg._100ms + BEST_MILLISECOND < Time_millis()) //100ms
{
stSysTime.flg._100ms = Time_millis();
Receive_data_Handel();//数据接收判断
IWDG_ReloadCounter();//清开门狗
}
}
}
4.3 OLED显示函数
/*******************************************************************************
* 函数名:OLED_Handel
* 描述 :OLED显示
* 输入 :void
* 输出 :void
* 调用 :初始化
* 备注 :100ms
*******************************************************************************/
void OLED_Handel(void)
{
if(ADC_Flag)
{
if(Interface_switching == 0)
{
OLED_Show_Character(1,1,0,16);//水
OLED_Show_Character(1,2,1,16);//质
OLED_Show_Character(1,3,13,16);//:
OLED_ShowNum(1,8,ADC2_Value,4);
OLED_ShowString(1, 13, "kg/s");
OLED_Show_Character(2,1,0,16);//水
OLED_Show_Character(2,2,2,16);//位
OLED_Show_Character(2,3,13,16);//:
OLED_ShowNum(2,8,ADC1_Value,4);
OLED_ShowString(2, 13, "mm");
OLED_Show_Character(3,1,11,16);//阈
OLED_Show_Character(3,2,12,16);//值
OLED_Show_Character(3,3,13,16);//:
OLED_ShowNum(3,8,ADC1_Threshold,4);
OLED_ShowString(3, 13, "mm");
if(++switching_count > 2)
{
OLED_Clear();
switching_count = 0;
Interface_switching = 1;
}
}
else if(Interface_switching == 1)
{
OLED_Show_Character(1,1,3,16);//雨
OLED_Show_Character(1,2,4,16);//量
OLED_Show_Character(1,3,13,16);//:
OLED_ShowNum(1,8,ADC3_Value,4);
OLED_ShowString(1, 13, "mm");
OLED_Show_Character(2,1,6,16);//流
OLED_Show_Character(2,2,7,16);//速
OLED_Show_Character(2,3,13,16);//:
OLED_ShowNum(2,8,ADC4_Value,4);
OLED_ShowString(2, 13, "m/s");
OLED_Show_Character(3,1,0,16);//水
OLED_Show_Character(3,2,8,16);//压
OLED_Show_Character(3,3,13,16);//:
OLED_ShowNum(3,8,ADC5_Value,4);
OLED_ShowString(3, 13, "Pa");
OLED_Show_Character(4,1,10,16);//风
OLED_Show_Character(4,2,7,16);//速
OLED_Show_Character(4,3,13,16);//:
OLED_ShowNum(4,8,ADC6_Value,4);
OLED_ShowString(4, 13, "m/s");
if(++switching_count > 2)
{
OLED_Clear();
switching_count = 0;
Interface_switching = 0;
}
}
}
}
二、总结
今天主要讲了基于STM32的水库预警系统的Proteus仿真。
感谢你的观看!