功能介绍:
0.本系统采用STC89C52作为单片机
1.LCD1602液晶实时显示温度,PWM档位值和当前转速,WIFI定时上报检测到的数据
2.可通过按键控制电机启动,停止加速,减速
3.温度超过50℃蜂鸣器报警,且电机停止转动,需要手动关闭报警后才可再次启动
4.采用DC002作为电源接口可直接输入5V给整个系统供电
原理图:
PCB :
主程序:
#include <reg52.h> //包含头文件,一般情况不需要改动,头文件包含特殊功能寄存器的定义
#include <stdio.h>
#include "18b20.h"
#include "lcd1602.h"
#include "delay.h"
#include "key.h"
/************************* 宏定义 *************************/
#define ON 0
#define OFF 1
/************************* 引脚定义 *************************/
sbit L9110_INA = P1^1;
sbit L9110_INB = P1^0;
sbit BUZZER = P2^2;
bit ReadTempFlag; //定义读时间标志
int temp; //温度读取
float temperature; //实际温度
xdata char dis0[36]; //定义显示区域临时存储数组
char dis1[8]; //定义显示区域临时存储数组
unsigned long time_20ms = 0;
unsigned char pwmValue = 5; //占空比调整
unsigned char pwmDisp; // pwm显示值
bit readRateFlag = 0; //读取速度标志
bit alarmFlag = 0; //报警标志
bit startFlag = 0;
unsigned int rate; //速度值
unsigned long pulseNum; //脉冲计数
unsigned char sendIndex = 0;
void Timer0_Init(void); //函数声明
void UART_Init(void); //串口初始化
void UART_SendByte(unsigned char dat); //串口发送单字节数据
void UART_SendStr(unsigned char *s, unsigned char length); //发送定长度字符串
void SendData(void);
/************************* 主函数 *************************/
void main(void)
{
L9110_INA = 1;
L9110_INB = 1;
Timer0_Init();
EX0 = 1; //外部中断0开
IT0 = 1; //边沿触发
LCD_Init(); //初始化液晶
DelayMs(20); //延时有助于稳定
LCD_DispStr(4, 0, "Welcome!");
DelayMs(200); //延时有助于稳定
DelayMs(200); //延时有助于稳定
DelayMs(200); //延时有助于稳定
while(!DS18B20_GetTemp(&temp)); //读取温度
temperature = (float)temp * 0.0625; //温度转换
UART_Init(); //串口初始化
/************************* WIFI模式配置 *************************/
UART_SendStr("AT+CIPMUX=1\r\n", 13); //打开多连接
DelayS(1);
UART_SendStr("AT+CIPSERVER=1,8080\r\n", 21); //建立服务 端口号为8080
// TR2 = 0; //关闭串口
LCD_Clear(); //清屏
while (1) //主循环
{
if (ReadTempFlag == 1) //读取温度标志
{
TR0 = 0;
EX0 = 0;
DS18B20_GetTemp(&temp); //读取温度
temperature = (float)temp * 0.0625; //温度转换
TR0 = 1;
EX0 = 1;
sprintf(dis0, "Now:%4.1f", temperature); //打印温度值
LCD_DispStr(0, 0, dis0);
LCD_DispOneChar(8, 0, 0xdf); //写入温度右上角点
LCD_DispOneChar(9, 0, 'C'); //写入字符C
if (startFlag == 1)
{
LCD_DispStr(10, 0, " Start");
}
else
{
LCD_DispStr(10, 0, " Stop ");
}
if (temperature > 50) //高于报警温度,报警并停止电机
{
alarmFlag = 1;
startFlag = 0;
} //只能通过手动取消报警
if (alarmFlag)
{
BUZZER = ON; //打开蜂鸣器
}
else
{
BUZZER = OFF; //关闭蜂鸣器
}
sprintf(dis1, "PWM:%03d ", (int)pwmValue*10); //打印温度值
LCD_DispStr(0, 1, dis1);
ReadTempFlag = 0;
}
if (readRateFlag == 1) //读取速度标志
{
readRateFlag = 0;
rate = pulseNum;
sprintf(dis1, "R:%03dr/s", rate); //打印速度
LCD_DispStr(8, 1, dis1);
SendData();
EX0 = 1;
pulseNum = 0;
}
KeyProcess(); //按键处理
}
}
/************************* WIFI串口发送数据 *************************/
void SendData(void)
{
sendIndex++;
if (sendIndex > 2)
{
sendIndex = 1;
}
if (sendIndex == 1) //发送命令
{
UART_SendStr("AT+CIPSEND=0,36\r\n", 17); //发送数据
}
if (sendIndex == 2) //发送数据
{
if (startFlag == 1)
{
sprintf(dis0, "Now:%4.1f'C Start\r\nPWM:%03d R:%03dr/s\r\n", temperature, (int)pwmValue * 10, rate); //串口发送
}
else
{
sprintf(dis0, "Now:%4.1f'C Stop \r\nPWM:%03d R:%03dr/s\r\n", temperature, (int)pwmValue * 10, rate); //串口发送
}
UART_SendStr(dis0, 36); //发送数据
}
}
void Timer0_Init(void)
{
TMOD |= 0x01; //使用模式1,16位定时器,使用"|"符号可以在使用多个定时器时不受影响
TL0 = 0x66; //设置定时初始值
TH0 = 0xFC; //设置定时初始值 1ms
PT0 = 1; //设置高优先级
EA = 0; //总中断关闭
ET0 = 1; //定时器中断打开
TR0 = 1; //定时器开关打开
}
/*------------------------------------------------
外部中断程序
------------------------------------------------*/
void ISR_Key(void) interrupt 0
{
pulseNum++;
}
void Timer0_isr(void) interrupt 1
{
static unsigned char IN1Count = 0;
static unsigned long numCount = 0;
TL0 = 0x66; //设置定时初始值
TH0 = 0xFC; //设置定时初始值 1ms
if (startFlag == 1)
{
IN1Count++;
if (IN1Count > pwmValue+15) //关闭时间段 +15是为了让电机达到最小启动值
{
L9110_INA = 1;
}
else if (IN1Count <= pwmValue+15) //占空比调节
{
L9110_INA = 0;
}
if (IN1Count > 10+15)
{
IN1Count = 0; //一个周期结束
}
}
else
{
L9110_INA = 1;
}
numCount++;
if (numCount > 1000) //1s
{
EX0 = 0;
readRateFlag = 1;
numCount = 0;
}
if (numCount % 500 == 0) // 500ms
{
ReadTempFlag = 1;
}
}
/************************* 串口配置 *************************/
void UART_Init(void)
{
SCON = 0x50;
TH2 = 0xFF;
TL2 = 0xFD;
RCAP2H = 0xFF; //(65536-(FOSC/32/BAUD)) BAUD = 115200 FOSC = 11059200
RCAP2L = 0xFD;
/*****************/
TCLK = 1;
RCLK = 1;
C_T2 = 0;
EXEN2 = 0;
/*****************/
TR2 = 1;
ES = 0; //关闭串口中断
EA = 1; //打开总中断
}
/************************* 串口发送字节 *************************/
void UART_SendByte(unsigned char dat) //串口发送单字节数据
{
unsigned char time_out;
time_out = 0;
SBUF = dat; //将数据放入SBUF中
while ((!TI) && (time_out < 100)) //检测是否发送出去
{
time_out++;
DelayUs10x(2);
} //未发送出去 进行短暂延时
TI = 0; //清除ti标志
}
/************************* 串口发送字符串 *************************/
void UART_SendStr(unsigned char *s, unsigned char length)
{
unsigned char num;
num = 0x00;
while (num < length) //发送长度对比
{
UART_SendByte(*s); //放松单字节数据
s++; //指针++
num++; //下一个++
}
}