蓝桥杯嵌入式第七届省赛——“模拟液位检测告警系统”旧板标准库

6 篇文章 0 订阅
6 篇文章 0 订阅

一、赛题分析

        模拟液位检测告警系统,涉及到KEY、ADC、EEPROM、LED、USART、LCD等模块。本届赛题相对简单,各个模块均可在往期文章中找到配置方法和编写说明。如:

蓝桥杯嵌入式——第六届省赛“电压测量监控设备”旧版标准库_对愁眠后霜满天的博客-CSDN博客

本届赛题主要难点在于对液位上升和下降趋势的判断,并通过串口发送至电脑。以及串口查询,和存储液面阀值。

二、程序设计

本届赛题所用到的模块均在往届赛题有所涉及,具体可查看往期文章或在文章最后下载本届赛题的项目工程。

1、对液面等级变化趋势的判断

        对于此处,博主的思想是:在while(1)之前要读取一次ADC采样值,判断level等级,并标记此时的液面等级。再在while(1)中level改变之前标记和改变之后的值进行对比,可得出液面变化趋势。

2、串口发送查询部分

        对于此处,题目中要求对接收一个字符数据的判断。所以可以先接收数据再判断是否满足条件,若不满足查询条件直接清除,若满足则发送查询数据,再清除接收数据。如果不清除接收数据,则多次串口发送后可能会出错。

void USART2_IRQHandler(void) 
{
	if(USART_GetITStatus(USART2,USART_IT_RXNE) != RESET)
	{
		USART_ClearITPendingBit(USART2,USART_IT_RXNE);		
		USART_RXBUF[RXCUNT++] = USART_ReceiveData(USART2);
		if(USART_RXBUF[0] != '\0')
		{
			USART_ITConfig(USART2,USART_IT_RXNE,ENABLE);
			RXOVER = 1; 
		}
	}
}
/*  此为部分,整体可在主函数中体现
	if(RXOVER == 1)
	{
		RXOVER = 0;
		RXCUNT = 0;
		if(USART_RXBUF[0] == 'C')
		{
			memset(string,0,sizeof(string));
			sprintf((char*)string,"C:H%d+L%d\\r\\n\r\n",Height,leve);	
			USART_SendString(USART2,string);	
			led3_flag = 1;
		}
		if(USART_RXBUF[0] == 'S')
		{
			memset(string,0,sizeof(string));
			sprintf((char*)string,"S:TL%d+TM%d+TH%d\\r\\n\r\n",TH.th_1,TH.th_2,TH.th_3);	
			USART_SendString(USART2,string);	
			led3_flag = 1;
		}		
		memset(USART_RXBUF,0,sizeof(USART_RXBUF));
	}
*/

3、main.c

        写I2C之后一定要延时5ms左右10ms比较保险,不然可能出错。

#include "stm32f10x.h"
#include "lcd.h"
#include "led.h"
#include "key.h"
#include "delay.h"
#include "adc.h"
#include "timer.h"
#include "usart.h"
#include "i2c.h"
#include "stdio.h"
#include "string.h"

struct Level{u8 th_1,th_2,th_3;}TH={30,50,70};
enum show_stat{Level,Setting};

u8 Height = 0,leve = 0,leve_flag = 0,select_flag = 0;
u8 ADC_Flag,led_flag = 0,key_flag = 0,show_flag = Level;
u8 led2_flag = 0,ld2 = 0,led3_flag = 0,ld3 = 0;
u8 string[20];
float adc_temp;

void key_in(void);
void show_lcd(void);
void highlight_char(u8 Line, u8 *ptr);
void height_leve(void);
void Leve_init(void);
void judgement_usart(void);
void led_state(void);
	
//Main Body
int main(void)
{
	STM3210B_LCD_Init();      
	LCD_Clear(Black);          
	LCD_SetBackColor(Black);  
	LCD_SetTextColor(White); 
	SysTick_Config(SystemCoreClock/1000);
	
	TIM4_Init();
	USART2_Init(9600);
	LED_Init();
	KEY_Init();
	ADC_INIT();
	i2c_init();
	
	TH.th_1 = i2c_read(0x32);
	if(TH.th_1 > 95&&TH.th_1%5 != 0)
		TH.th_1 = 30;
	TH.th_2 = i2c_read(0x33);
	if(TH.th_2 > 95&&TH.th_2%5 != 0)
		TH.th_2 = 50;	
	TH.th_3 = i2c_read(0x34);
	if(TH.th_3 > 95&&TH.th_3%5 != 0)
		TH.th_3 = 70;	
	
	Leve_init();
	while(1)
	{
		key_in();
		show_lcd();
		led_state();
	}
}

void Leve_init(void)
{
	adc_temp = Read_ADC();
	Height = adc_temp * 100 / 3.3;
	height_leve();
	leve_flag = leve;
}

void key_in(void)
{
	key_flag = key_scan();
	if(key_flag == 1)
	{
		show_flag =! show_flag;
		LCD_Clear(Black);
	}
	if(key_flag == 2&&show_flag == Setting)
	{
		select_flag = (select_flag + 1) % 3;
	}
	if(key_flag == 3&&show_flag == Setting)
	{
		if(select_flag == 0&&TH.th_1<95)TH.th_1 = TH.th_1 + 5;
		if(select_flag == 1&&TH.th_2<95)TH.th_2 = TH.th_2 + 5;
		if(select_flag == 2&&TH.th_3<95)TH.th_3 = TH.th_3 + 5;
		i2c_write(0x32,TH.th_1);Delay_Ms(10);
		i2c_write(0x33,TH.th_2);Delay_Ms(10);
		i2c_write(0x34,TH.th_3);Delay_Ms(10);
	}
	if(key_flag == 4&&show_flag == Setting)
	{
		if(select_flag == 0&&TH.th_1>5)TH.th_1 = TH.th_1 - 5;
		if(select_flag == 1&&TH.th_2>5)TH.th_2 = TH.th_2 - 5;
		if(select_flag == 2&&TH.th_3>5)TH.th_3 = TH.th_3 - 5;
		i2c_write(0x32,TH.th_1);Delay_Ms(10);
		i2c_write(0x33,TH.th_2);Delay_Ms(10);
		i2c_write(0x34,TH.th_3);Delay_Ms(10);
	}
}

void show_lcd(void)
{
	if(ADC_Flag)
	{
		ADC_Flag = 0;
		adc_temp = Read_ADC();
	}
	if(show_flag == Level)
	{
		LCD_DisplayStringLine(Line1,(u8*)"    Liquid Level    ");
		
		Height = adc_temp * 100 / 3.3;
		memset(string,0,sizeof(string));
		sprintf((char*)string,"  Height:%dcm  ",Height);
		LCD_DisplayStringLine(Line3,string);
		
		memset(string,0,sizeof(string));
		sprintf((char*)string,"     ADC:%.2fV  ",adc_temp);
		LCD_DisplayStringLine(Line5,string);
		
		judgement_usart();
		
		memset(string,0,sizeof(string));
		sprintf((char*)string,"   Level:%d  ",leve);
		LCD_DisplayStringLine(Line7,string);	
	}else if(show_flag == Setting)
	{
		LCD_DisplayStringLine(Line1,(u8*)"   Parameter Setup   ");
		
		memset(string,0,sizeof(string));
		sprintf((char*)string," Threshold1:%dcm  ",TH.th_1);
		if(select_flag == 0)highlight_char(Line3,string);		
		else LCD_DisplayStringLine(Line3,string);		
		
		memset(string,0,sizeof(string));
		sprintf((char*)string," Threshold2:%dcm  ",TH.th_2);
		if(select_flag == 1)highlight_char(Line5,string);
		else LCD_DisplayStringLine(Line5,string);	
		
		memset(string,0,sizeof(string));
		sprintf((char*)string," Threshold3:%dcm  ",TH.th_3);
		if(select_flag == 2)highlight_char(Line7,string);
		else LCD_DisplayStringLine(Line7,string);	
	}
}

void highlight_char(u8 Line, u8 *ptr)
{
	u32 i = 0;
	u16 refcolumn = 319;
	while ((*ptr != 0) && (i < 20))	 
	{
		LCD_SetTextColor(Yellow);
		LCD_DisplayChar(Line, refcolumn, *ptr);
		LCD_SetTextColor(White);
		refcolumn -= 16;
		ptr++;
		i++;
	}
}

void judgement_usart(void)
{
	leve_flag = leve;
	height_leve();
	if(leve_flag>leve)
	{
		memset(string,0,sizeof(string));
		sprintf((char*)string,"A:H%d+L%d+D\\r\\n\r\n",Height,leve);	
		USART_SendString(USART2,string);
		led2_flag = 1;
	}
	if(leve_flag<leve)
	{
		memset(string,0,sizeof(string));
		sprintf((char*)string,"A:H%d+L%d+U\\r\\n\r\n",Height,leve);	
		USART_SendString(USART2,string);
		led2_flag = 1;
	}
	leve_flag = leve;
	
	if(RXOVER == 1)
	{
		RXOVER = 0;
		RXCUNT = 0;
		if(USART_RXBUF[0] == 'C')
		{
			memset(string,0,sizeof(string));
			sprintf((char*)string,"C:H%d+L%d\\r\\n\r\n",Height,leve);	
			USART_SendString(USART2,string);	
			led3_flag = 1;
		}
		if(USART_RXBUF[0] == 'S')
		{
			memset(string,0,sizeof(string));
			sprintf((char*)string,"S:TL%d+TM%d+TH%d\\r\\n\r\n",TH.th_1,TH.th_2,TH.th_3);	
			USART_SendString(USART2,string);	
			led3_flag = 1;
		}		
		memset(USART_RXBUF,0,sizeof(USART_RXBUF));
	}
}

void height_leve(void)
{
	if(Height<=TH.th_1)leve = 0;
	else if(Height>TH.th_1&&Height<=TH.th_2)leve = 1;
	else if(Height>TH.th_2&&Height<=TH.th_3)leve = 2;
	else leve = 3;
}

void led_state(void)
{
	LED_Control(LED1,led_flag);
	LED_Control(LED2,ld2);
	LED_Control(LED3,ld3);
}

void TIM4_IRQHandler(void)
{
	static u16 led_cnt = 0,led2_cnt = 0,led3_cnt = 0;
	if (TIM_GetITStatus(TIM4,TIM_IT_Update) != RESET)
	{
		TIM_ClearITPendingBit(TIM4, TIM_IT_Update);
		if(++led_cnt>=1000)
		{
			led_cnt = 0;
			led_flag =! led_flag;
		}
		if(led2_flag == 1)
		{
			if(++led2_cnt%200 == 0)
				ld2 =! ld2;
			if(led2_cnt>=2000){led2_cnt = 0;led2_flag = 0;ld2=0;}
		}
		if(led3_flag == 1)
		{
			if(++led3_cnt%200 == 0)
				ld3 =! ld3;
			if(led3_cnt>=2000){led3_cnt = 0;led3_flag = 0;ld3=0;}
		}
	}
}

三、工程附上

链接:https://pan.baidu.com/s/1mD5Mwb8kkYdkKlSh0Y9uhg 
提取码:foao

有不对的地方,请多指教...

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

对愁眠后霜满天

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值