这些小活动你都参加了吗?快来围观一下吧!>>
电子产品世界 » 论坛首页 » DIY与开源设计 » 电子DIY » 【Let'sdo第四期-液体流量检测仪DIY】-成果分享帖

共1条 1/1 1 跳转至

【Let'sdo第四期-液体流量检测仪DIY】-成果分享帖

菜鸟
2025-01-25 22:16:35     打赏

成果展示视频:【【Let's do第四期】DIY液体流量检测仪-项目展示】 https://www.bilibili.com/video/BV1wJfZYpEsj/?vd_source=1b092d899318d2ac63cda1ed6ce04937

EETV成果视频链接:https://v.eepw.com.cn/video/play/id/16227 


本期给大家分享一下我的制作成果。

液体流量监测仪:

  1. 按键双击快速控制水泵开关;

  2. 按键长按 选择开关状态,或者选择定量值设定,任意值可设,由于精度差异,设定步进值为50ml;

  3. 总流量累计;

功能模块设计调试:

  1. 搭建keil环境;

  2. OLED 显示。

  3. 继电器控制抽水泵通断。

  4. 实现流量计测量功能。

  5. 实现定量 任意 水量控制。

KEY_FLAG Key_s; //声明一个按键结构体变量
/*===========================  单击 双击 长按  =============================*/

void key_det_1(void)
{
    Key_s.key_1 = (~Buttons_GetState()) & (1 << 0);
	 // printf ("%d\\n\\r",Key_s.key_1);
    if(Key_s.key_flag_1 == 1)  //单击 
    {
        Key_s.key_flag_1  = 0;
        Key_s.key_resault = 1;
    }
    else if(Key_s.key_flag_1 == 2)  //长按
    {
        Key_s.key_flag_1  = 0;
        Key_s.key_resault = 2;
    }
    else if(Key_s.key_flag_1 == 3)//双击
    {
        Key_s.key_flag_1  = 0;
        Key_s.key_resault = 3;
			   
    }
    
    switch(Key_s.key_state)
    {
        case 0:
            if(Key_s.key_1 == 0)                 //按下
            {
                if(++Key_s.key_cnt_1 > 5)         //主循环进来一次  作用:按下消抖  
                {
                    Key_s.key_cnt_1 = 0;
                    Key_s.key_state = 1;
									  
                }
            }
            else
            {
                Key_s.key_cnt_1 = 0;
            }
        break;
        case 1:
            if(Key_s.key_1 == 1)                 //松开
            {
                Key_s.key_cnt_1 = 0;
                Key_s.key_state = 2;
							  return; 
            }
            if(++Key_s.key_cnt_1 >= 200)          
            {
                Key_s.key_cnt_1 = 0;
                Key_s.key_state = 3;
                Key_s.key_flag_1 = 2;            //长按事件
							  
                return; 
            }
        break;
        case 2:
            if(Key_s.key_1 == 0)                //按下
            {
                Key_s.key_cnt_1 = 0;
                Key_s.key_state = 3;
                Key_s.key_flag_1 = 3;             //双击判断
							  
                return; 
            }
            if(++Key_s.key_cnt_1 >= 40)         // 计时超过400ms判断为单击事件
            {
                Key_s.key_cnt_1 = 0;
                Key_s.key_flag_1 = 1;             //单击事件
                Key_s.key_state = 3;
							 
                return;  
            }
        break;
        case 3:
            if(Key_s.key_1 == 1)                //松开
            {
                Key_s.key_state = 0;
							 
            }
        break;
        default:
            Key_s.key_state = 0;            
    }
    
    Key_s.key_flag_1 = 0;    
}
void UI_Disply(void)
{
	switch(StrFlow.step)
	{
		case 0:
			   OLED_ShowChinese(16*0,16+5,0,16,1);    
				 OLED_ShowChinese(16*1,16+5,1,16,1);    
				 OLED_ShowChinese(16*2,16+5,2,16,1);    
				 OLED_ShowChinese(16*3,16+5,3,16,1);    
				 OLED_ShowChinese(16*4,16+5,4,16,1);    
				 OLED_ShowChinese(16*5,16+5,5,16,1);    
				 OLED_ShowChinese(16*6,16+5,6,16,1);    
				 OLED_ShowChinese(16*7,16+5,7,16,1);
		     StrFlow.step = 1;
		     OLED_Refresh();
		     delay_ms(2000);
		     OLED_Clear();
			break;
		case 1:
		
			OLED_ShowChinese(16*0,16*0,8,16,1);          
			OLED_ShowChinese(16*1,16*0,4,16,1);      OLED_ShowChar(16*2 ,16*0,':',16,1);     
																															 
			OLED_ShowChinese(16*0,16*1+5*1,2,16,1);                   
			OLED_ShowChinese(16*1,16*1+5*1,3,16,1);  OLED_ShowChar(16*2 ,16*1+5*1,':',16,1);
																																
			OLED_ShowChinese(16*0,16*2+5*2,2,16,1);                   
			OLED_ShowChinese(16*1,16*2+5*2,4,16,1);  OLED_ShowChar(16*2 ,16*2+5*2,':',16,1);

			OLED_ShowNum(OLED_X_I ,16*0    ,StrFlow.SetmL,5,16,1);
			OLED_ShowNum(OLED_X_I ,16*1+5*1,StrFlow.QmL,5,16,1);
			OLED_ShowNum(OLED_X_I ,16*2+5*2,StrFlow.TotalmL*1,5,16,1);//0.

			OLED_ShowString(16*5+5,16*0,    "ml",    16,1);                     
			OLED_ShowString(16*5+5,16*1+5*1,"ml/S",16,1);                 
			OLED_ShowString(16*5+5,16*2+5*2,"ml",    16,1);
		
	 
			if(!StrFlow.Ctr_Relay)
			{
				 OLED_ShowString(128-25,16*0,    "OFF",16,1);      
			}
			else
			{
				 OLED_ShowString(128-25,16*0,    "ON ",16,1);   
			}
		
		StrFlow.step = 0xFF;
			break;
 
		
		default:
			
		  OLED_ShowNum(OLED_X_I ,16*1+5*1,StrFlow.QmL,5,16,1);
		  OLED_ShowNum(OLED_X_I ,16*2+5*2,StrFlow.TotalmL,5,16,1);
      switch(Key_s.key_resault)
			{
				case CLICK_DOUBLE:
 
								 (StrFlow.Ctr_Relay == 0)?(StrFlow.Ctr_Relay = 1):(StrFlow.Ctr_Relay = 0);
									if(!StrFlow.Ctr_Relay)
									{
										  GPIO_PinWrite    (GPIOA, 8,  Switch_Relay(false));           									
									}
									else
									{
										  
									   FlowSetup();
										 GPIO_PinWrite    (GPIOA, 8,  Switch_Relay(true));
									}

					break;
				case CLICK_LONG:
					    switch(GetCursor)
							{
								case 0:
										 GetCursor = 1;
								    
									   if(!StrFlow.Ctr_Relay)
										 {
											 Switch_Relay(false);  
										 }
										 else if(1==StrFlow.Ctr_Relay)
										 {
											 Switch_Relay(true);  
										 }
								          
									break;
								case 1:
										  GetCursor = 2;
										  OLED_ShowNum(OLED_X_I ,16*0    ,StrFlow.SetmL,5,16,0);       
									break;
								default:
									    if(StrFlow.SetmL>10 && StrFlow.Ctr_Relay==1)
											{
												GPIO_PinWrite    (GPIOA, 8, Switch_Relay(true));
											}
									break;
								
							}
					break;
				case CLICK:
					    switch(GetCursor)
							{
								case 1:
									   (StrFlow.Ctr_Relay == 0)?(StrFlow.Ctr_Relay = 1):(StrFlow.Ctr_Relay = 0);
								      if(!StrFlow.Ctr_Relay)
											{
												 OLED_ShowString(128-25,16*0,    "OFF",16,1);      
											}
										  else
											{
												 OLED_ShowString(128-25,16*0,    "ON ",16,1);   
											}
											GetCursor = 2;
									break;
								case 2:     
								      OLED_ShowNum(OLED_X_I ,16*0    ,StrFlow.SetmL+=50,5,16,0);  
									break;
								
							}
					break;
			}
	
		    
       		Key_s.key_resault = 0;
	 break;	
	
	}
 
}

以上就是主要代码和实现功能的方式,很高兴您能看到这里。 希望可以帮助你。

由于没有多少事件细化代码,代码比较乱,就不开源了,如果群友们有要求,那我就抽时间整理后再开源。

在这里先感谢DigiKey联合EEPW举办的此次活动,不仅有老师在线讲解还有众多群友的帮助完成任务。期待下一次的活动。





关键词: 液体     霍尔传感器     stm32F103RB     液体流量    

共1条 1/1 1 跳转至

回复

匿名不能发帖!请先 [ 登陆 注册 ]