大三上学期我们就要做课程设计了,之前的学长学姐都是十个人一组,到我们老师觉得十个人太水就把我们弄成了三人一组,然后让我们用一个多月的时间去做物联网节点设计。
开始后一两天就给我们每组发了开发板,一款是普中的51单片机开发板,一款是正点原子的潘多拉开发板,然后就让我们自己选题开工了。我之前学STM32的时候买了几个核心板、蓝牙模块和TFT屏幕,然后就打算用手上有的东西区实现了。
程序写到一半,我们又去问了老师几个问题,老师跟我们讲说还要自己做电路设计,最少要有焊接过程,正好之前我还有PCB设计的一些经验,虽然不是很会,但当时觉得做一个这样的小板子应该不成问题。
最后就开始动手了。
Github地址:https://github.com/sin1111yi/STM32F1-HC05-board
之前学STM32的时候,用的是野火的F103指南者开发板,又买了几个C8T6和RCT6的开发板。最初学STM32的动力也是在B站上看到别人的一个视频,自己做了双模的蓝牙键盘,当时觉得有点意思也想自己试试,然后就开始学这个了。
2.1.1 原理图设计
原理图做了好多参照(复制) ,最后得到了缝合怪开发板。因为是基于蓝牙的节点设计,所以选择直接板载蓝牙模块,然后就去参照了正点原子ATK-HC05的原理图。
把这个集成到电路板上就可以让老师比较信服这个是我们自己做的,因为当时板子做出来老师也对这个板子的来源有一点怀疑,当然最终还是相信了。
最后剩下的就是把别人的原理图照着画一遍,得到最终的原理图。
2.1.2 PCB设计
原理图用立创EDA画出来,然后用AutoCAD做了一个边框,EDA转换成PCB后导入边框层,最后排原件走线。唯一要注意的就是蓝牙模块天线要放在边缘,并且下面不要敷铜。
PCB就这样画好了,然后当然就是薅羊毛5元打样然后做SMT,做SMT的时候有的元件没有的话也只能自己买回来焊接。
成品做出来后就开始烧程序,最初上电的时候看上去都没有问题,蓝牙模块也正常运行了起来了,但是烧程序就执行不了,一直卡在HardFault_Handler()。做了一天debug,最后发现是BOOT0没有拉低,抱着死马当活马医的心态换了把它换成了磁珠,结果就好了。
实际上Type-C接口也是不能用的,所以我也没有去测试CH340部分能不能使用。
最终成品就是这样,也就是它陪着我走完了课程设计的这段路,也许下个学期还会继续用它。
整个任务之前也说了是由三个人一起完成,我负责这个节点,其他两个人各负责一个节点,他们两个用学校发的51单片机开发板,我用上面做的这个板子。
设计上,我们打算做的是智能家居系统,本来的设想很宏大,结果实现起来都是在下位机出了问题,最后只能一直缩减,最后完全按照计划做出来的也只有上位机。
程序流程直接贴一个图
最后看指导书要求还能统计网络流量,就用TIM2做了一个定时,然后收发数据包都计数,两秒算一次就能得到网络内的数据流量。
代码上串口通信用了USART1和USART2,直接移植了野火的代码。滴答定时器也是移植,TFT显示也是移植,自己只写了几个函数让它可以做到自动换行和半屏清空,用来做分开显示。
main.c
#include
#include
#include "HC_05.h"
#include "Host_usart.h"
#include "TFT_LCD.h"
#include "RGB.h"
#include "General_TIM.h"
/**
* @author sin1111yi
* @date 2020/12/19
* @brief now it can use usart2(PA2, PA3) to send or receive data
* change _MODE_ to change start mode
*/
#define _MODE_ 1 // 0-Quick Start 1-Normal Start
#if _USE_HOST_USART_1_
extern volatile uint8_t StrLen1;
extern volatile uint8_t USART1_RECV_END_FLAG;
#endif
#if _USE_HOST_USART_2_
extern volatile uint8_t StrLen1;
extern volatile uint8_t USART2_RECV_END_FLAG;
#endif
extern volatile uint32_t Real_T;
extern volatile uint8_t flag;
uint32_t TIM2_Time = 0;
//Used in Monitor_Init() and stm32f10x_it.c
uint32_t SendPack = 0;
uint32_t RecvPack = 0;
uint32_t SendBits = 0;
uint32_t RecvBits = 0;
char SendMonitor[8] = {0};
char RecvMonitor[8] = {0};
uint16_t i = 0, j = 0, k = 0;
void System_StartUp(void);
void Monitor_Init(void);
void DataTraf_Display(void);
#if _USE_HOST_USART_1_
void USART1_Loop(void);
void USART1_Wait(void);
#endif
#if _USE_HOST_USART_2_
void USART2_Loop(void);
void USART2_Wait(void);
#endif
int main()
{
System_StartUp();
Monitor_Init();
GENERAL_TIM_Init();
while (1)
{
DataTraf_Display();
#if _USE_HOST_USART_1_
USART1_Loop();
SysTick_DelaySyncUs(200);
#endif
#if _USE_HOST_USART_2_
USART2_Loop();
#endif
SysTick_DelaySync(200);
LCD_Clear(WHITE);
}
}
void System_StartUp()
{
LCD_Init();
LED_Init();
HOST_Usart_Config();
LED_Red(On);
#if _USE_HOST_USART_1_
memset(USART1_DataBuff, 0, 128 * sizeof(char));
memset(USART1_RecvBuff, 0, 128 * sizeof(char));
memset(USART1_SendBuff, 0, 128 * sizeof(char));
#endif
#if _USE_HOST_USART_2_
memset(USART2_DataBuff, 0, 128 * sizeof(char));
memset(USART2_RecvBuff, 0, 128 * sizeof(char));
memset(USART2_SendBuff, 0, 128 * sizeof(char));
#endif
#if _MODE_
LCD_Clear(WHITE);
SysTick_DelaySyncUs(50);
LCD_Clear(RED);
SysTick_DelaySyncUs(50);
LCD_Clear(GREEN);
SysTick_DelaySyncUs(50);
LCD_Clear(BLUE);
SysTick_DelaySyncUs(50);
LCD_Clear(BLACK);
LCD_Clear(WHITE);
LCD_Showimage(18, 10, 89, 89, gImage_ZMYsWork);
LCD_CharsDisaplay(30, 105, GRAY1, WHITE, "By 969Yay");
SysTick_DelaySync(500);
LCD_Clear(YELLOW);
LCD_CharsDisaplay(28, 58, YELLOW, GREEN, "CQUPT2020");
SysTick_DelaySync(1000);
LCD_Clear(GRAY2);
LCD_CharsDisaplay(10, 10, WHITE, GRAY2, "MADE BY:");
LCD_CharsDisaplay(10, 40, WHITE, GRAY2, "Member 1");
LCD_CharsDisaplay(10, 70, WHITE, GRAY2, "Member 2");
LCD_CharsDisaplay(10, 100, WHITE, GRAY2, "Member 3");
SysTick_DelaySync(1000);
LCD_Clear(BLACK);
#endif
#if !_MODE_
LCD_Clear(BLACK);
SysTick_DelaySync(500);
LCD_CharsDisaplay(18, 56, RED, BLACK, "Quick Start!");
SysTick_DelaySync(1000);
#endif
LCD_Clear(WHITE);
LED_Red(Off);
}
void Monitor_Init(void)
{
SendPack = 0;
RecvPack = 0;
SendBits = 0;
RecvBits = 0;
SendMonitor[4] = 'B';
SendMonitor[5] = '/';
SendMonitor[6] = 's';
RecvMonitor[4] = 'B';
RecvMonitor[5] = '/';
RecvMonitor[6] = 's';
}
void DataTraf_Display(void)
{
LCD_CharsDisaplay(4, 4, RED, WHITE, "SEND: ");
LCD_CharsDisaplay(50, 4, BLACK, WHITE, SendMonitor);
LCD_CharsDisaplay(4, 108, RED, WHITE, "RECV: ");
LCD_CharsDisaplay(50, 108, BLACK, WHITE, RecvMonitor);
}
#if _USE_HOST_USART_1_
void USART1_Loop(void)
{
HOST_UsartSendByte(HOST_USART1, HC05_HOSTCmds[2]);
SendPack++;
if (USART1_RECV_END_FLAG == 1)
{
LED_Green(On);
SysTick_DelaySyncUs(100);
USART1_RECV_END_FLAG = 0;
HOST_UsartSendString(HOST_USART1, USART1_RecvBuff);
if (flag)
{
LCD_HalfClear(RED, 0);
LED_Red_On;
LCD_CharsDisaplay(16, 30, WHITE, RED, "WARNING :");
LCD_DisplayOneChar(80, 30, WHITE, RED, USART1_RecvBuff[0]);
LCD_DisplayOneChar(88, 30, WHITE, RED, USART1_RecvBuff[1]);
LCD_DisplayOneChar(96, 30, WHITE, RED, USART1_RecvBuff[2]);
}
else
{
LED_Red_Off;
LCD_CharsDisaplay(4, 30, BLACK, WHITE, "Temperature:");
All_LCD_CharsDisplay(8, 46, GREEN, WHITE, USART1_RecvBuff);
memset(USART1_RecvBuff, 0, 128 * sizeof(char));
SysTick_DelaySync(200);
//LCD_HalfClear(WHITE, 0);
}
LED_Green(Off);
return;
}
USART1_Wait();
return;
}
void USART1_Wait()
{
LCD_CharsDisaplay(8, 32, BLACK, WHITE, "Waiting");
for (i = 0; i < 3; i++)
{
LCD_CharsDisaplay(64 + 8 * i, 32, BLACK, WHITE, ". ");
if (USART1_RECV_END_FLAG == 1)
{
LCD_Clear(WHITE);
return;
}
SysTick_DelaySync(300);
}
for (i = 0; i < 3; i++)
{
LCD_CharsDisaplay(88 - 8 * i, 32, BLACK, WHITE, " ");
if (USART1_RECV_END_FLAG == 1)
{
LCD_Clear(WHITE);
return;
}
SysTick_DelaySync(300);
}
}
#endif
#if _USE_HOST_USART_2_
void USART2_Loop(void)
{
HOST_UsartSendByte(HOST_USART2, HC05_HOSTCmds[3]);
SendPack++;
if (USART2_RECV_END_FLAG == 1)
{
LED_Blue(On);
SysTick_DelaySyncUs(100);
USART2_RECV_END_FLAG = 0;
HOST_UsartSendString(HOST_USART2, USART2_RecvBuff);
LCD_CharsDisaplay(4, 70, BLACK, WHITE, "Illumination:");
All_LCD_CharsDisplay(8, 86, BLUE, WHITE, USART2_RecvBuff);
memset(USART2_RecvBuff, 0, 128 * sizeof(char));
SysTick_DelaySyncUs(200);
//LCD_HalfClear(WHITE, 1);
LED_Blue(Off);
return;
}
USART2_Wait();
return;
}
void USART2_Wait()
{
LCD_CharsDisaplay(8, 80, BLACK, WHITE, "Waiting");
for (i = 0; i < 3; i++)
{
LCD_CharsDisaplay(64 + 8 * i, 80, BLACK, WHITE, ". ");
if (USART2_RECV_END_FLAG == 1)
{
LCD_Clear(WHITE);
return;
}
SysTick_DelaySync(300);
}
for (i = 0; i < 3; i++)
{
LCD_CharsDisaplay(88 - 8 * i, 80, BLACK, WHITE, " ");
if (USART2_RECV_END_FLAG == 1)
{
LCD_Clear(WHITE);
return;
}
SysTick_DelaySync(300);
}
}
#endif
stm32f10x_it.c
/* Includes ------------------------------------------------------------------*/
#include "stm32f10x_it.h"
#include "HC_05.h"
#include "Host_usart.h"
#include "RGB.h"
#include "TFT_LCD.h"
#include "General_TIM.h"
#include
#include
/* User Variable -------------------------------------------------------------*/
// HOST_USART1_IRQHandler()
volatile uint8_t StrLen1 = 0;
volatile uint8_t USART1_RECV_END_FLAG = 0;
// HOST_USART2_IRQHandler()
volatile uint8_t StrLen2 = 0;
volatile uint8_t USART2_RECV_END_FLAG = 0;
//for data processing
volatile uint32_t Real_T = 0;
volatile uint8_t flag = 0;
extern volatile uint32_t TIM2_Time; //TIM2
//Data traffic mointor
extern uint32_t SendPack;
extern uint32_t RecvPack;
extern uint32_t SendBits;
extern uint32_t RecvBits;
extern char SendMonitor[8];
extern char RecvMonitor[8];
#define Warning_T 295 //29.5 degree C
/** @addtogroup STM32F10x_StdPeriph_Template
* @{
*/
/* Private typedef -----------------------------------------------------------*/
/* Private define ------------------------------------------------------------*/
/* Private macro -------------------------------------------------------------*/
/* Private variables ---------------------------------------------------------*/
/* Private function prototypes -----------------------------------------------*/
/* Private functions ---------------------------------------------------------*/
/******************************************************************************/
/* Cortex-M3 Processor Exceptions Handlers */
/******************************************************************************/
/**
* @brief This function handles NMI exception.
* @param None
* @retval None
*/
void NMI_Handler(void)
{
}
/**
* @brief This function handles Hard Fault exception.
* @param None
* @retval None
*/
void HardFault_Handler(void)
{
/* Go to infinite loop when Hard Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Memory Manage exception.
* @param None
* @retval None
*/
void MemManage_Handler(void)
{
/* Go to infinite loop when Memory Manage exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Bus Fault exception.
* @param None
* @retval None
*/
void BusFault_Handler(void)
{
/* Go to infinite loop when Bus Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles Usage Fault exception.
* @param None
* @retval None
*/
void UsageFault_Handler(void)
{
/* Go to infinite loop when Usage Fault exception occurs */
while (1)
{
}
}
/**
* @brief This function handles SVCall exception.
* @param None
* @retval None
*/
void SVC_Handler(void)
{
}
/**
* @brief This function handles Debug Monitor exception.
* @param None
* @retval None
*/
void DebugMon_Handler(void)
{
}
/**
* @brief This function handles PendSVC exception.
* @param None
* @retval None
*/
void PendSV_Handler(void)
{
}
/**
* @brief This function handles SysTick Handler.
* SysTick_Handler has already defined in "SysTick.h"
* @param None
* @retval None
*/
/*
void SysTick_Handler(void)
{
}
*/
/**
* @brief Serial interrupt service function
* defined in "Host_usart.h"
* @param None
* @retval None
*/
#if _USE_HOST_USART_1_
void HOST_USART1_IRQHandler()
{
if (USART_GetFlagStatus(HOST_USART1, USART_IT_RXNE) == SET)
{
if (USART_ReceiveData(HOST_USART1) == '\n')
{
StrLen1 = 0;
USART1_RECV_END_FLAG = 1;
Real_T = ((uint32_t)USART1_RecvBuff[0] - '0') * 1000 +
((uint32_t)USART1_RecvBuff[1] - '0') * 100 +
((uint32_t)USART1_RecvBuff[2] - '0') * 10 +
((uint32_t)USART1_RecvBuff[4] - '0');
if (Real_T >= Warning_T)
flag = 1;
else
flag = 0;
memset(USART1_DataBuff, 0, 128 * sizeof(char));
}
else
{
if (StrLen1 == 0)
memset(USART1_RecvBuff, 0, 128 * sizeof(char));
USART1_DataBuff[StrLen1] = USART_ReceiveData(HOST_USART1);
USART1_RecvBuff[StrLen1] = USART1_DataBuff[StrLen1];
StrLen1++;
}
RecvPack++;
}
if (USART_GetITStatus(HOST_USART1, USART_IT_RXNE) != RESET)
USART_ClearITPendingBit(HOST_USART1, USART_IT_RXNE);
}
#endif
#if _USE_HOST_USART_2_
void HOST_USART2_IRQHandler()
{
if (USART_GetFlagStatus(HOST_USART2, USART_IT_RXNE) == SET)
{
if (USART_ReceiveData(HOST_USART2) == '\n')
{
StrLen2 = 0;
USART2_RECV_END_FLAG = 1;
memset(USART2_DataBuff, 0, 128 * sizeof(char));
}
else
{
if (StrLen2 == 0)
memset(USART2_RecvBuff, 0, 128 * sizeof(char));
USART2_DataBuff[StrLen2] = USART_ReceiveData(HOST_USART2);
USART2_RecvBuff[StrLen2] = USART2_DataBuff[StrLen2];
StrLen2++;
}
RecvPack++;
}
if (USART_GetITStatus(HOST_USART2, USART_IT_RXNE) != RESET)
USART_ClearITPendingBit(HOST_USART2, USART_IT_RXNE);
}
#endif
void GENERAL_TIM_IRQHandler(void)
{
if (TIM_GetITStatus(GENERAL_TIM, TIM_IT_Update) != RESET)
{
TIM2_Time++;
if (TIM2_Time == 2000)
{
TIM2_Time = 0;
SendBits = SendPack * 8 / 2;
RecvBits = RecvPack * 8 / 2;
SendMonitor[0] = SendBits / 1000 + '0';
SendMonitor[1] = (SendBits % 1000) / 100 + '0';
SendMonitor[2] = (SendBits % 100) / 10 + '0';
SendMonitor[3] = SendBits % 10 + '0';
RecvMonitor[0] = RecvBits / 1000 + '0';
RecvMonitor[1] = (RecvBits % 1000) / 100 + '0';
RecvMonitor[2] = (RecvBits % 100) / 10 + '0';
RecvMonitor[3] = RecvBits % 10 + '0';
SendPack = 0;
RecvPack = 0;
SendBits = 0;
RecvBits = 0;
}
TIM_ClearITPendingBit(GENERAL_TIM, TIM_FLAG_Update);
}
}
/******************************************************************************/
/* STM32F10x Peripherals Interrupt Handlers */
/* Add here the Interrupt Handler for the used peripheral(s) (PPP), for the */
/* available peripheral interrupt handler's name please refer to the startup */
/* file (startup_stm32f10x_xx.s). */
/******************************************************************************/
/**
* @brief This function handles PPP interrupt request.
* @param None
* @retval None
*/
/*void PPP_IRQHandler(void)
{
}*/
/**
* @}
*/
/******************* (C) COPYRIGHT 2011 STMicroelectronics *****END OF FILE****/
体验还行,找队友一定要靠谱,这次也多亏了队友靠谱才能顺利完成。