#include "action_process.h" #include "sw_timer.h" #include "gpio_switch.h" #include "gpio_state_led.h" #include "gpio_sensor.h" #include "eeprom.h" #include "buzzer.h" #include "segment.h" #include "save_file.h" #include "kcd_hp100.h" #include "rtc_process.h" #include "save_file.h" #define KEY_POWER KEY_PUSH_SW1 #define KEY_MODE_SET KEY_PUSH_SW2 #define KEY_UP KEY_PUSH_SW3 #define KEY_DOWN KEY_PUSH_SW4 typedef enum _control_step { CONTROL_STEP_INIT, CONTROL_STEP_INIT_BUZZER_ON, CONTROL_STEP_INIT_ALL_LED_ON, CONTROL_STEP_INIT_ALL_LED_ON_WAIT, CONTROL_STEP_INIT_VERSION_ON, CONTROL_STEP_INIT_VERSION_ON_WAIT, CONTROL_STEP_INIT_POWER_ON_KEY_SET, CONTROL_STEP_INIT_COMPLETE, CONTROL_STEP_ACTION_IDLE, CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA, CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA, CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA, CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA, CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA, CONTROL_STEP_ACTION_RUN_COMPLETE, }CONTROL_STEP; typedef struct _control_info { bool isInitView; bool isActionRun; bool isRelayOn; CONTROL_STEP Step; uint32_t StartTickCount; uint32_t GetSensorDataTickCount; uint32_t returnMainViewTickCount; uint16_t Co2_Now; uint16_t Co2_SaveData; uint16_t Co2_MaxValue; uint16_t Co2_MinValue; uint16_t Co2_TempValue; SET_INDEX SetIndex; uint16_t Co2_TempMax; uint16_t Co2_TempMin; }CONTROL_INFO; uint8_t SaveCheckSec = 0xFF; uint16_t SaveSensorIndex; uint16_t SaveSensorCo2[100]; static CONTROL_INFO Control_Info; static void Action_Process(void); static void Action_PowerOn_Init_Process(void); static void Action_PowerOn_Process(void); static void Action_Get_SensorData(void); static void Action_Get_SensorReadProcess(void); static void Action_SaveSensorData(void); static void Action_Power_On_Key_Set(void); static void Action_Power_On_Key_Push_Callback(void); static void Action_Power_Off_Key_Set(void); static void Action_Power_Off_Key_Push_Callback(void); static void Action_Mode_Key_Push(void); static void Action_Set_Key_Push(void); static void Action_Up_Key_Push(void); static void Action_Down_Key_Push(void); static void Action_ReturnMainViewCheck(void); static void Action_Relay_Output_Check(void); static void Action_RelayOn(void); static void Action_RelayOff(void); void Action_Initialization(void) { Control_Info.isInitView = false; Control_Info.Step = CONTROL_STEP_INIT; Gpio_Swtich_Set_Callback(KEY_MODE_SET, Action_Mode_Key_Push, Action_Set_Key_Push, NULL); Gpio_Swtich_Set_Callback(KEY_UP, Action_Up_Key_Push, NULL, NULL); Gpio_Swtich_Set_Callback(KEY_DOWN, Action_Down_Key_Push, NULL, NULL); SW_Timer_Callback_Register(SW_TIMER_RUN_CONTINUE, 1, Action_Process); } static void Action_Process(void) { if(Control_Info.isInitView == false) { Action_PowerOn_Init_Process(); } else { if(Control_Info.isActionRun == true) Action_PowerOn_Process(); } } static void Action_PowerOn_Init_Process(void) { uint8_t i; switch(Control_Info.Step) { case CONTROL_STEP_INIT: Control_Info.Step = CONTROL_STEP_INIT_BUZZER_ON; break; case CONTROL_STEP_INIT_BUZZER_ON: Buzzer_On(500); Control_Info.Step = CONTROL_STEP_INIT_ALL_LED_ON; break; case CONTROL_STEP_INIT_ALL_LED_ON: Segment_All_Set_Data(0xFF); for(i = 0 ; i < GPIO_LED_MAX ; i++) { Gpio_Led_OutputSet(i, GPIO_LED_MODE_ON, 0, 0); } Control_Info.StartTickCount = millis(); Control_Info.Step = CONTROL_STEP_INIT_ALL_LED_ON_WAIT; break; case CONTROL_STEP_INIT_ALL_LED_ON_WAIT: if((millis() - Control_Info.StartTickCount) >= ACTION_INIT_LED_ON_WAIT_TIME) { Control_Info.Step = CONTROL_STEP_INIT_VERSION_ON; } break; case CONTROL_STEP_INIT_VERSION_ON: Segment_Show_Version(); Control_Info.StartTickCount = millis(); Control_Info.Step = CONTROL_STEP_INIT_VERSION_ON_WAIT; break; case CONTROL_STEP_INIT_VERSION_ON_WAIT: if((millis() - Control_Info.StartTickCount) >= ACTION_INIT_LED_ON_WAIT_TIME) { Segment_All_Set_Data(0x00); for(i = 0 ; i < GPIO_LED_MAX ; i++) { Gpio_Led_OutputSet(i, GPIO_LED_MODE_OFF, 0, 0); } Control_Info.Step = CONTROL_STEP_INIT_POWER_ON_KEY_SET; } break; case CONTROL_STEP_INIT_POWER_ON_KEY_SET: Gpio_Led_OutputSet(GPIO_LED_LE1, GPIO_LED_MODE_TOGGLE, ACTION_LE1_IDLE_ON_TIME, ACTION_LE1_IDLE_OFF_TIME); Action_Power_On_Key_Set(); Control_Info.Step = CONTROL_STEP_INIT_COMPLETE; break; case CONTROL_STEP_INIT_COMPLETE: Control_Info.isInitView = true; Control_Info.Step = CONTROL_STEP_ACTION_IDLE; break; } } static void Action_PowerOn_Process(void) { switch (Control_Info.Step) { case CONTROL_STEP_INIT: Action_Power_Off_Key_Set(); Gpio_Led_OutputSet(GPIO_LED_LE1, GPIO_LED_MODE_TOGGLE, ACTION_LE1_RUN_ON_TIME, ACTION_LE1_RUN_OFF_TIME); Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_ON, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_OFF, 0, 0); Action_RelayOff(); GPIO_SENSOR_PWR_ON; SaveCheckSec = 0xFF; Control_Info.Co2_Now = 0xFFFF; Control_Info.Co2_SaveData = 0xFFFF; Action_Get_SensorData(); if(EEPROM_Read_SettingValue(&Control_Info.Co2_MaxValue, &Control_Info.Co2_MinValue) == false) { Control_Info.Co2_MaxValue = DEFAULT_SENSOR_MAX_DATA; Control_Info.Co2_MinValue = DEFAULT_SENSOR_MIN_DATA; } Control_Info.Co2_TempMax = 0; Control_Info.Co2_TempMin = 0xFFFF; printf("Data, Time, Average(Now)_Co2, Max_Co2, Min_Co2, Relay\r\n"); Control_Info.Step = CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA; break; case CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA: Segment_Show_Time(); Segment_Show_SensorData(Control_Info.Co2_Now); break; case CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA: Segment_Show_Time(); Segment_Show_SensorData(Control_Info.Co2_MaxValue); break; case CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA: Segment_Show_Time(); Segment_Show_SensorData(Control_Info.Co2_MinValue); break; case CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA: case CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA: Segment_Show_Time(); Segment_Show_SettingData(Control_Info.SetIndex, Control_Info.Co2_TempValue); break; case CONTROL_STEP_ACTION_RUN_COMPLETE: Gpio_Led_OutputSet(GPIO_LED_LE1, GPIO_LED_MODE_TOGGLE, ACTION_LE1_IDLE_ON_TIME, ACTION_LE1_IDLE_OFF_TIME); Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_OFF, 0, 0); GPIO_SENSOR_PWR_OFF; Action_Power_On_Key_Set(); Segment_All_Set_Data(0x00); Action_RelayOff(); EEPROM_Write_SettingValue(Control_Info.Co2_MaxValue, Control_Info.Co2_MinValue); Control_Info.Step = CONTROL_STEP_ACTION_IDLE; Control_Info.isActionRun = false; return; break; } //////////////////////////////////////// Action_Get_SensorReadProcess(); Action_ReturnMainViewCheck(); } static void Action_Power_On_Key_Set(void) { Gpio_Swtich_Set_PushCount(KEY_POWER, DEFAULT_KEY_PUSH_COUNT, KEY_POWER_ON_CHECK_PUSH_COUNT); Gpio_Swtich_Set_Callback(KEY_POWER, NULL, Action_Power_On_Key_Push_Callback, NULL); } static void Action_Power_Off_Key_Set(void) { Gpio_Swtich_Set_PushCount(KEY_POWER, DEFAULT_KEY_PUSH_COUNT, KEY_POWER_OFF_CHECK_PUSH_COUNT); Gpio_Swtich_Set_Callback(KEY_POWER, NULL, Action_Power_Off_Key_Push_Callback, NULL); } static void Action_Power_On_Key_Push_Callback(void) { Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.isActionRun = true; Control_Info.Step = CONTROL_STEP_INIT; } static void Action_Power_Off_Key_Push_Callback(void) { Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.Step = CONTROL_STEP_ACTION_RUN_COMPLETE; } static void Action_Get_SensorData(void) { Control_Info.GetSensorDataTickCount = millis(); KCD_HP100_Tx_Get_MeasurmentData(); } static void Action_Get_SensorReadProcess(void) { KCD_HP100_STATE nowSensorState = KCD_HP100_GetState(); if(nowSensorState == KCD_HP100_SUCCESS) { KCD_HP100_Get_Co2((uint16_t *)&Control_Info.Co2_Now); Control_Info.Co2_SaveData = Control_Info.Co2_Now; if(Control_Info.Co2_Now >= Control_Info.Co2_MaxValue) { Action_RelayOff(); } else if(Control_Info.Co2_Now <= Control_Info.Co2_MinValue) { Action_RelayOn(); } } else if(nowSensorState == KCD_HP100_ERROR_TIMEOUT) { Control_Info.Co2_Now = 0xFFFF; } if(millis() - Control_Info.GetSensorDataTickCount >= ACTION_SENSOR_READ_INTERVAL) { if(nowSensorState == KCD_HP100_SUCCESS) { RTC_TIME nowTime; nowTime = RTC_Get_Time(); if(Control_Info.Co2_TempMax < Control_Info.Co2_Now) Control_Info.Co2_TempMax = Control_Info.Co2_Now; if(Control_Info.Co2_TempMin > Control_Info.Co2_Now) Control_Info.Co2_TempMin = Control_Info.Co2_Now; printf("Now, %04d-%02d-%02d %02d:%02d:%02d, %d, %d, %d, %d\r\n", nowTime.rtc_Year, nowTime.rtc_Month, nowTime.rtc_Date, nowTime.rtc_Hour, nowTime.rtc_Min, nowTime.rtc_Sec, Control_Info.Co2_Now, Control_Info.Co2_TempMax, Control_Info.Co2_TempMin, Control_Info.isRelayOn); } Action_Get_SensorData(); } Action_SaveSensorData(); } static void Action_SaveSensorData(void) { RTC_TIME nowTime; nowTime = RTC_Get_Time(); if(SaveCheckSec != nowTime.rtc_Sec) { SaveCheckSec = nowTime.rtc_Sec; if(nowTime.rtc_Sec == 0) { if(Control_Info.Co2_SaveData != 0xFFFF){ SaveSensorCo2[SaveSensorIndex++] = Control_Info.Co2_SaveData; } if(nowTime.rtc_Min % 5 == 0) { if(SaveSensorIndex >= 5) { uint8_t i; uint16_t Sum_Co2, Max_Co2, Min_Co2; Max_Co2 = 0; Min_Co2 = 0xFFFF; Sum_Co2 = 0; for(i = 0 ; i < SaveSensorIndex ; i++) { Sum_Co2 += SaveSensorCo2[i]; if(SaveSensorCo2[i] >= Max_Co2) { Max_Co2 = SaveSensorCo2[i]; } if(SaveSensorCo2[i] <= Min_Co2) { Min_Co2 = SaveSensorCo2[i]; } } Sum_Co2 -= Max_Co2; Sum_Co2 -= Min_Co2; Sum_Co2 /= (SaveSensorIndex - 2); if(Save_SensorData_SDCard(Sum_Co2, Max_Co2, Min_Co2, Control_Info.isRelayOn ? 0xFF : 0x00) == false) { printf("Save fail, %04d-%02d-%02d %02d:%02d:%02d, %d, %d, %d, %d\r\n", nowTime.rtc_Year, nowTime.rtc_Month, nowTime.rtc_Date, nowTime.rtc_Hour, nowTime.rtc_Min, nowTime.rtc_Sec, Sum_Co2, Max_Co2, Min_Co2, Control_Info.isRelayOn); } else { printf("Save, %04d-%02d-%02d %02d:%02d:%02d, %d, %d, %d, %d\r\n", nowTime.rtc_Year, nowTime.rtc_Month, nowTime.rtc_Date, nowTime.rtc_Hour, nowTime.rtc_Min, nowTime.rtc_Sec, Sum_Co2, Max_Co2, Min_Co2, Control_Info.isRelayOn); } } SaveSensorIndex = 0; } } } } static void Action_ReturnMainViewCheck(void) { if(Control_Info.Step != CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA){ if(millis() - Control_Info.returnMainViewTickCount >= ACTION_RETURN_MAINVIEW_TIME){ Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_ON, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_OFF, 0, 0); Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA; } } } static void Action_RelayOn(void) { if(Control_Info.isRelayOn == false){ Control_Info.isRelayOn = true; Gpio_Led_OutputSet(GPIO_LED_D4, GPIO_LED_MODE_ON, 0, 0); GPIO_RELAY_ON; } } static void Action_RelayOff(void) { if(Control_Info.isRelayOn == true){ Control_Info.isRelayOn = false; Gpio_Led_OutputSet(GPIO_LED_D4, GPIO_LED_MODE_OFF, 0, 0); GPIO_RELAY_OFF; } } void Action_Set_MaxMin_Value(uint16_t MaxValue, uint16_t MinValue) { Control_Info.Co2_MaxValue = MaxValue; Control_Info.Co2_MinValue = MinValue; EEPROM_Write_SettingValue(Control_Info.Co2_MaxValue, Control_Info.Co2_MinValue); } static void Action_Mode_Key_Push(void) { switch(Control_Info.Step) { case CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA: Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_ON, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_OFF, 0, 0); Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA; break; case CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA: Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_ON, 0, 0); Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA; break; case CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA: Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Gpio_Led_OutputSet(GPIO_LED_D1, GPIO_LED_MODE_OFF, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D2, GPIO_LED_MODE_ON, 0, 0); Gpio_Led_OutputSet(GPIO_LED_D3, GPIO_LED_MODE_OFF, 0, 0); Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_NOW_SENSOR_DATA; break; case CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA: case CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA: Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); switch(Control_Info.SetIndex) { case SET_1000: case SET_100: case SET_10: Control_Info.SetIndex++; break; case SET_1: Control_Info.SetIndex = SET_1000; break; } break; } } static void Action_Set_Key_Push(void) { if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA){ Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.Co2_TempValue = Control_Info.Co2_MaxValue; Control_Info.SetIndex = SET_1000; Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA; } else if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA){ Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.Co2_TempValue = Control_Info.Co2_MinValue; Control_Info.SetIndex = SET_1000; Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA; } else if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA){ Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.Co2_MaxValue = Control_Info.Co2_TempValue; Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_MAX_SENSOR_DATA; EEPROM_Write_SettingValue(Control_Info.Co2_MaxValue, Control_Info.Co2_MinValue); } else if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA){ Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.Co2_MinValue = Control_Info.Co2_TempValue; Control_Info.returnMainViewTickCount = millis(); Control_Info.Step = CONTROL_STEP_ACTION_RUN_MIN_SENSOR_DATA; EEPROM_Write_SettingValue(Control_Info.Co2_MaxValue, Control_Info.Co2_MinValue); } } static void Action_Up_Key_Push(void) { if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA || Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA) { uint16_t temp; Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.returnMainViewTickCount = millis(); switch(Control_Info.SetIndex) { case SET_1000: Control_Info.Co2_TempValue += 1000; if(Control_Info.Co2_TempValue >= 10000){ Control_Info.Co2_TempValue -= 10000; } break; case SET_100: temp = Control_Info.Co2_TempValue / 100; temp = temp % 10; if(temp == 9){ Control_Info.Co2_TempValue -= 900; } else{ Control_Info.Co2_TempValue += 100; } break; case SET_10: temp = Control_Info.Co2_TempValue / 10; temp = temp % 10; if(temp == 9){ Control_Info.Co2_TempValue -= 90; } else{ Control_Info.Co2_TempValue += 10; } break; case SET_1: temp = Control_Info.Co2_TempValue % 10; if(temp == 9){ Control_Info.Co2_TempValue -= 9; } else{ Control_Info.Co2_TempValue++; } break; } } } static void Action_Down_Key_Push(void) { if(Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MAX_SENSOR_DATA || Control_Info.Step == CONTROL_STEP_ACTION_RUN_SET_MIN_SENSOR_DATA) { uint16_t temp; Buzzer_On(DEFAULT_KEY_PUSH_BUZZER_TIME_COUNT); Control_Info.returnMainViewTickCount = millis(); switch(Control_Info.SetIndex) { case SET_1000: temp = Control_Info.Co2_TempValue / 1000; if(temp == 0){ Control_Info.Co2_TempValue += 9000; } else{ Control_Info.Co2_TempValue -= 1000; } break; case SET_100: temp = Control_Info.Co2_TempValue / 100; temp = temp % 10; if(temp == 0){ Control_Info.Co2_TempValue += 900; } else{ Control_Info.Co2_TempValue -= 100; } break; case SET_10: temp = Control_Info.Co2_TempValue / 10; temp = temp % 10; if(temp == 0){ Control_Info.Co2_TempValue += 90; } else{ Control_Info.Co2_TempValue -= 10; } break; case SET_1: temp = Control_Info.Co2_TempValue % 10; if(temp == 0){ Control_Info.Co2_TempValue += 9; } else{ Control_Info.Co2_TempValue--; } break; } } }