# HG changeset patch # User Ethan Zonca # Date 2016-07-06 18:54:18 # Node ID d87613e49192a0d535137854f26969ed2cc3988e # Parent a5edaa5d3c45a641ab196ad2a2c948d5e5dc5e7b Added support for adjustable hysteresis in thermostatic mode. Also fixed missing logo rendering on initial powerup. diff --git a/config.h b/config.h --- a/config.h +++ b/config.h @@ -46,6 +46,7 @@ #define DEFAULT_IGNORE_ERROR 0 #define DEFAULT_SETPOINT_BREW 70 #define DEFAULT_SETPOINT_STEAM 70 +#define DEFAULT_HYSTERESIS 1 #endif diff --git a/display.c b/display.c --- a/display.c +++ b/display.c @@ -25,7 +25,7 @@ static uint8_t sw_right_last = 0; static uint8_t trigger_drawsetpoint = 1; static int16_t last_temp = 21245; static int16_t last_temp_frac = 21245; -static int16_t last_state = STATE_IDLE; +static int16_t last_state = 123; static uint8_t goto_mode = MODE_HEAT; static uint8_t reset_mode = RESET_REBOOT; @@ -190,7 +190,7 @@ void display_process(therm_settings_t* s if(set->val.control_mode == MODE_PID) status->state = STATE_SETP; else - status->state = STATE_SETBOOTTOBREW; + status->state = STATE_SETHYSTERESIS; } else if (!HAL_GPIO_ReadPin(SW_UP)) { set->val.plant_type = PLANT_COOLER; @@ -204,6 +204,35 @@ void display_process(therm_settings_t* s } break; + + case STATE_SETHYSTERESIS: + { + // Write text to OLED + ssd1306_drawstring("Hysteresis", 0, 40); + ssd1306_drawlogo(); + + char tempstr[6]; + itoa(set->val.hysteresis, tempstr, 10); + ssd1306_drawstring("H=", 1, 45); + ssd1306_drawstring(" ", 1, 57); + ssd1306_drawstring(tempstr, 1, 57); + + ssd1306_drawstring("Press to accept", 3, 40); + + // Button handler + if(SW_BTN_PRESSED) { + status->state = STATE_SETBOOTTOBREW; + } + else { + user_input((uint16_t*)&set->val.hysteresis); + } + + // Event Handler + // N/A + + } break; + + case STATE_SETP: { // Write text to OLED diff --git a/flash.c b/flash.c --- a/flash.c +++ b/flash.c @@ -40,6 +40,7 @@ void flash_load_defaults(therm_settings_ torestore->val.ignore_error = DEFAULT_IGNORE_ERROR; torestore->val.setpoint_brew = DEFAULT_SETPOINT_BREW; torestore->val.setpoint_steam = DEFAULT_SETPOINT_STEAM; + torestore->val.hysteresis = DEFAULT_HYSTERESIS; } static void __flash_write(therm_settings_t* tosave) diff --git a/main.c b/main.c --- a/main.c +++ b/main.c @@ -92,6 +92,8 @@ int main(void) uint32_t last_thermostat = 0; int16_t ssr_output = 0; // Duty cycle of ssr, 0 to SSR_PERIOD + uint8_t thermostat_plant_on = 0; + // Main loop while(1) { @@ -180,16 +182,20 @@ int main(void) temp_frac = status.temp > 0 ? temp_frac : temp_frac * -1; int32_t temp = (status.temp * 10) + temp_frac; - uint8_t plant_on = 0; // EMZ FIXME: This could be way simpler - if(set.val.plant_type == PLANT_HEATER && status.setpoint * 10 < temp) - plant_on = 1; - else if(set.val.plant_type == PLANT_COOLER && status.setpoint * 10 > temp) - plant_on = 1; + if(set.val.plant_type == PLANT_HEATER && status.setpoint * 10 < temp - set.val.hysteresis * 10) + thermostat_plant_on = 1; + else if(set.val.plant_type == PLANT_HEATER && status.setpoint * 10 > temp + set.val.hysteresis * 10) + thermostat_plant_on = 0; + + if(set.val.plant_type == PLANT_COOLER && status.setpoint * 10 > temp + set.val.hysteresis * 10) + thermostat_plant_on = 1; + else if(set.val.plant_type == PLANT_COOLER && status.setpoint * 10 < temp - set.val.hysteresis * 10) + thermostat_plant_on = 0; // EMZ: TODO: Refactor to output_enabled or something - if(status.pid_enabled && plant_on) + if(status.pid_enabled && thermostat_plant_on) { // EMZ TODO: functionalize this // put ssr output on display diff --git a/states.h b/states.h --- a/states.h +++ b/states.h @@ -29,6 +29,7 @@ typedef union int32_t setpoint_steam; uint32_t control_mode; uint32_t plant_type; + uint32_t hysteresis; } val; uint16_t data[128]; @@ -44,6 +45,7 @@ enum state { STATE_SETMODE, STATE_SETPLANTTYPE, + STATE_SETHYSTERESIS, STATE_SETP, STATE_SETI, STATE_SETD,