蓝桥杯嵌入式第七届国赛程序----温、湿度监控设备

Kefira ·
更新时间:2024-09-20
· 855 次阅读

本届国赛题目较为综合,涉及adc、串口、输入捕获、输出比较等。

工程结构

init.c

#include "stm32f10x.h" #include "lcd.h" #include "init.h" #include "i2c.h" void GPIO_Int(void) { GPIO_InitTypeDef GPIO_InitStructure; ADC_InitTypeDef ADC_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC|RCC_APB2Periph_GPIOD, ENABLE); //led GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10| GPIO_Pin_11| GPIO_Pin_12| GPIO_Pin_13| GPIO_Pin_14| GPIO_Pin_15; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP; GPIO_Init(GPIOC, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2; GPIO_Init(GPIOD, &GPIO_InitStructure); //key //led GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_0; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU; GPIO_Init(GPIOA, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1|GPIO_Pin_2; GPIO_Init(GPIOB, &GPIO_InitStructure); GPIO_SetBits(GPIOC,GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10| GPIO_Pin_11| GPIO_Pin_12| GPIO_Pin_13| GPIO_Pin_14| GPIO_Pin_15); GPIO_SetBits(GPIOD,GPIO_Pin_2); GPIO_ResetBits(GPIOD,GPIO_Pin_2); //adc GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN; GPIO_Init(GPIOB, &GPIO_InitStructure); ADC_InitStructure.ADC_Mode = ADC_Mode_Independent; ADC_InitStructure.ADC_ScanConvMode = DISABLE; ADC_InitStructure.ADC_ContinuousConvMode = ENABLE; ADC_InitStructure.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None; ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right; ADC_InitStructure.ADC_NbrOfChannel = 1; ADC_Init(ADC1, &ADC_InitStructure); /* ADC1 regular channel8 configuration */ ADC_RegularChannelConfig(ADC1, ADC_Channel_8, 1, ADC_SampleTime_13Cycles5); /* Enable AWD interrupt */ ADC_ITConfig(ADC1, ADC_IT_AWD, ENABLE); /* Enable ADC1 */ ADC_Cmd(ADC1, ENABLE); /* Enable ADC1 reset calibration register */ ADC_ResetCalibration(ADC1); /* Check the end of ADC1 reset calibration register */ while(ADC_GetResetCalibrationStatus(ADC1)); /* Start ADC1 calibration */ ADC_StartCalibration(ADC1); /* Check the end of ADC1 calibration */ while(ADC_GetCalibrationStatus(ADC1)); NVIC_Configuration(); } void TIM2_Init(void) { TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; GPIO_InitTypeDef GPIO_InitStructure; TIM_OCInitTypeDef TIM_OCInitStructure; /* TIM3 clock enable */ RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE); /* GPIOA clock enable */ RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_Init(GPIOA, &GPIO_InitStructure); TIM_TimeBaseStructure.TIM_Period = 999; TIM_TimeBaseStructure.TIM_Prescaler = 71; TIM_TimeBaseStructure.TIM_ClockDivision = 0; TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure); /* PWM1 Mode configuration: Channel1 */ TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM1; TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; TIM_OCInitStructure.TIM_Pulse = 500; TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; TIM_OC2Init(TIM2, &TIM_OCInitStructure); TIM_Cmd(TIM2, ENABLE); } void TIM3_Init(void) { TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; GPIO_InitTypeDef GPIO_InitStructure; TIM_ICInitTypeDef TIM_ICInitStructure; /* TIM3 clock enable */ RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); /* GPIOA clock enable */ RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; GPIO_Init(GPIOA, &GPIO_InitStructure); TIM_TimeBaseStructure.TIM_Period = 65535; TIM_TimeBaseStructure.TIM_Prescaler = 71; TIM_TimeBaseStructure.TIM_ClockDivision = 0; TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); TIM_ICInitStructure.TIM_Channel = TIM_Channel_2; TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising; TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI; TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1; TIM_ICInitStructure.TIM_ICFilter = 0x0; TIM_ICInit(TIM3, &TIM_ICInitStructure); TIM_SelectSlaveMode(TIM3,TIM_SlaveMode_Reset); TIM_SelectInputTrigger(TIM3,TIM_TS_TI2FP2); /* TIM enable counter */ TIM_Cmd(TIM3, ENABLE); } void LCD_Init(void) { STM3210B_LCD_Init(); LCD_Clear(Blue); LCD_SetBackColor(Blue); LCD_SetTextColor(White); SysTick_Config(SystemCoreClock/1000); LCD_DisplayStringLine(Line0," Real-time Data "); //LCD_DisplayStringLine(Line1,"Now Temp -20C "); LCD_DisplayStringLine(Line2," "); //LCD_DisplayStringLine(Line3,"Now Humi 60% "); LCD_DisplayStringLine(Line4," "); //LCD_DisplayStringLine(Line5,"Clock 12-50-00 "); LCD_DisplayStringLine(Line6," "); //LCD_DisplayStringLine(Line7,"Number 20 "); LCD_DisplayStringLine(Line8," "); LCD_DisplayStringLine(Line9," "); } void USART2_Init(void) { USART_InitTypeDef USART_InitStructure; GPIO_InitTypeDef GPIO_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO, ENABLE); RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING; GPIO_Init(GPIOA, &GPIO_InitStructure); GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2; GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOA, &GPIO_InitStructure); USART_InitStructure.USART_BaudRate = 9600; USART_InitStructure.USART_WordLength = USART_WordLength_8b; USART_InitStructure.USART_StopBits = USART_StopBits_1; USART_InitStructure.USART_Parity = USART_Parity_No; USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; USART_InitStructure.USART_Mode = USART_Mode_Rx |USART_Mode_Tx ; USART_Init(USART2, &USART_InitStructure); USART_ITConfig(USART2, USART_IT_RXNE, ENABLE); USART_Cmd(USART2, ENABLE); } void NVIC_Configuration(void) { NVIC_InitTypeDef NVIC_InitStructure; /* Configure the NVIC Preemption Priority Bits */ NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1); /* Enable the USART2 Interrupt */ NVIC_InitStructure.NVIC_IRQChannel = USART2_IRQn; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=0; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); } unsigned char I2C_Read(unsigned char add) { unsigned char temp; I2CStart(); I2CSendByte(0xa0); I2CSendAck(); I2CSendByte(add); I2CSendAck(); I2CStart(); I2CSendByte(0xa1); I2CSendAck(); temp=I2CReceiveByte(); I2CSendAck(); I2CStop(); return temp; } void I2C_Write(unsigned char add,unsigned char dat) { I2CStart(); I2CSendByte(0xa0); I2CSendAck(); I2CSendByte(add); I2CSendAck(); I2CSendByte(dat); I2CSendAck(); I2CStop(); }

主程序

/* 温度与数模转换的关系 T=kN+b,(N为模数转换值,T是温度) 由已知条件得 T=80N/4095-20; 湿度与捕获值得关系 H=m/C+n;(C为捕获值,H是湿度) 由已知条件得 H=(8000/C+10)/9 */ #include "stm32f10x.h" #include "lcd.h" #include "init.h" #include "i2c.h" #include "stdio.h" u32 TimingDelay = 0; u8 string[20]; void Key_Scan(void); void Delay_Ms(u32 nTime); unsigned int TIM3_Cap(void); void USART2_Send(u8 *str); void ADC_Read(void); void LED_Disp(u16 led); u8 miao_flag=0; u16 miao=0; u8 fazhi=0,shuju=0; u16 led=0; int i; signed char scTemp,scTemp1; unsigned char ucHumi,ucHumi1,ucFreq; //eeprom只能存整数,所以这里的频率是实际频率的一百分之一 unsigned char ucHour,ucMin,ucSec; unsigned char ucDataNo=0,ucDataNum=0,Data[60][5]; unsigned long ulTick_ms=0; unsigned char ucInte; unsigned long ulSec=0,ulSec1=0,ulSec2=0; u8 shezhi=0,qie=0; //Main Body int main(void) { LCD_Init(); GPIO_Int(); TIM2_Init(); TIM3_Init(); i2c_init(); USART2_Init(); Delay_Ms(5); if(I2C_Read(0x20)!=0) { Delay_Ms(5); I2C_Write(0x20,0); Delay_Ms(5); I2C_Write(0x00,40); Delay_Ms(5); I2C_Write(0x01,80); Delay_Ms(5); I2C_Write(0x02,1); Delay_Ms(5); I2C_Write(0x03,15); } Delay_Ms(5); scTemp1=I2C_Read(0x00); Delay_Ms(5); ucHumi1=I2C_Read(0x01); Delay_Ms(5); ucInte=I2C_Read(0x02); Delay_Ms(5); ucFreq=I2C_Read(0x03); TIM_SetAutoreload(TIM2,10000/ucFreq-1); //周期值 TIM_SetCompare2(TIM2,5000/ucFreq-1); //占比1/2 while(1) { Key_Scan(); if(fazhi==1) { fazhi=0; sprintf((char*)string,"C %02u-%02u-%02u %3dC %2u%%\r\n",ucHour,ucMin,ucSec,scTemp1,ucHumi1); USART2_Send(string); } else if(shuju==1) { shuju=0; for(i=0;i<ucDataNum;i++) { sprintf((char*)string,"S %02u-%02u-%02u %3dC %2u%%\r\n",Data[i][0],Data[i][1],Data[i][2],Data[i][3],Data[i][4]); USART2_Send(string); } } ADC_Read(); LED_Disp(led); } } void Key_Scan(void) { if(RB1==0) { Delay_Ms(5); if(RB1==0) { if(shezhi==0) { shezhi=1; LCD_DisplayStringLine(Line0," Parameter Setup "); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); } else if(shezhi==1) { shezhi=0; LCD_DisplayStringLine(Line0," Real-time Data "); Delay_Ms(5); I2C_Write(0x00,scTemp1); Delay_Ms(5); I2C_Write(0x01,ucHumi1); Delay_Ms(5); I2C_Write(0x02,ucInte); Delay_Ms(5); I2C_Write(0x03,ucFreq); } }while(!RB1); } else if(RB2==0) { Delay_Ms(5); if(RB2==0) { if(shezhi==1) { if(qie==0||qie==4) { qie=1; LCD_SetTextColor(Red); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); LCD_SetTextColor(White); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); } else if(qie==1) { qie=2; LCD_SetTextColor(Red); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); LCD_SetTextColor(White); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); } else if(qie==2) { qie=3; LCD_SetTextColor(Red); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); LCD_SetTextColor(White); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); } else if(qie==3) { qie=4; LCD_SetTextColor(Red); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); LCD_SetTextColor(White); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); } } }while(!RB2); } else if(RB3==0) { Delay_Ms(5); if(RB3==0) { if(shezhi==1) { if(qie==1) { if(scTemp1<60) scTemp1+=1; LCD_SetTextColor(Red); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); LCD_SetTextColor(White); } else if(qie==2) { if(ucHumi1<90) ucHumi1+=5; LCD_SetTextColor(Red); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); LCD_SetTextColor(White); } else if(qie==3) { if(ucInte<5) ucInte+=1; LCD_SetTextColor(Red); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); LCD_SetTextColor(White); } else if(qie==4) { if(ucFreq-20) scTemp1-=1; LCD_SetTextColor(Red); sprintf((char*)string,"Temp Upper:%3dC ",scTemp1); LCD_DisplayStringLine(Line1,string); LCD_SetTextColor(White); } else if(qie==2) { if(ucHumi1>10) ucHumi1-=5; LCD_SetTextColor(Red); sprintf((char*)string,"Humi Upper:%3d%% ",ucHumi1); LCD_DisplayStringLine(Line3,string); LCD_SetTextColor(White); } else if(qie==3) { if(ucInte>1) ucInte-=1; LCD_SetTextColor(Red); sprintf((char*)string,"Interval : %1us ",ucInte); LCD_DisplayStringLine(Line5,string); LCD_SetTextColor(White); } else if(qie==4) { if(ucFreq>10) ucFreq-=5; LCD_SetTextColor(Red); sprintf((char*)string,"Frequency :%2u.%1ukHz ",ucFreq/10,ucFreq%10); LCD_DisplayStringLine(Line7,string); LCD_SetTextColor(White); TIM_SetAutoreload(TIM2,10000/ucFreq-1); TIM_SetCompare2(TIM2,5000/ucFreq-1); } } }while(!RB4); } } void Delay_Ms(u32 nTime) { TimingDelay = nTime; while(TimingDelay != 0); } void ADC_Read(void) { if(shezhi==0) { if(ulSec!=ulSec1) { ulSec1=ulSec; ADC_SoftwareStartConvCmd(ADC1, ENABLE); scTemp=(ADC_GetConversionValue(ADC1)*80)/0xfff-20; sprintf((char*)string,"Now Temp %3dC ",scTemp); LCD_DisplayStringLine(Line1,string); ucHumi=(80000/TIM3_Cap()+10)/9; sprintf((char*)string,"Now Humi %3d%% ",ucHumi); LCD_DisplayStringLine(Line3,string); sprintf((char*)string,"Clock %02u-%02u-%02u ",ucHour,ucMin,ucSec); LCD_DisplayStringLine(Line5,string); sprintf((char*)string,"Number %2u ",ucDataNum); LCD_DisplayStringLine(Line7,string); } if((ulSec-ulSec2)>=ucInte) { ulSec2=ulSec; Data[ucDataNo][0]=ucHour; Data[ucDataNo][1]=ucMin; Data[ucDataNo][2]=ucSec; Data[ucDataNo][3]=scTemp; Data[ucDataNo][4]=ucHumi; if(++ucDataNo==60)ucDataNo=0; if(ucDataNum!=60)ucDataNum++; sprintf((char*)string,"Number %2u ",ucDataNum); LCD_DisplayStringLine(Line7,string); led^=4; } } } unsigned int TIM3_Cap(void) { if(TIM_GetFlagStatus(TIM3,TIM_FLAG_CC2)) { return TIM_GetCapture2(TIM3)+1; } else return 0; } void USART2_IRQHandler(void) { u8 temp; if(USART_GetITStatus(USART2, USART_IT_RXNE) != RESET) { USART_ClearITPendingBit(USART2, USART_IT_RXNE); temp = USART_ReceiveData(USART2); if(temp == 'C') { fazhi=1; } else if(temp=='S') { shuju=1; } } } void USART2_Send(u8 *str) { u8 index=0; do{ USART_SendData(USART2,str[index++]); while(USART_GetFlagStatus(USART2,USART_FLAG_TXE)==RESET); }while(str[index]!=0); } void LED_Disp(u16 led) { GPIO_Write(GPIOC,~led<=scTemp1) { if(ulTick_ms%200==0) led^=1; } else led&=0xfe; if(ucHumi>=ucHumi1) { if(ulTick_ms%200==0) led^=2; } else led&=0xfd; }
作者:初入江湖的郭大侠



监控 蓝桥杯 程序 嵌入 嵌入式

需要 登录 后方可回复, 如果你还没有账号请 注册新账号