254 lines
		
	
	
		
			13 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			254 lines
		
	
	
		
			13 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
| """
 | |
| uv-belichter-software - the SETTINGS submenu
 | |
| Copyright (C) 2024  Benjamin Burkhardt
 | |
| 
 | |
| This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
 | |
| 
 | |
| This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
 | |
| 
 | |
| You should have received a copy of the GNU General Public License along with this program.  If not, see <https://www.gnu.org/licenses/>.
 | |
| """
 | |
| 
 | |
| from time import sleep, time_ns
 | |
| 
 | |
| # All the arguments this method takes are there for one reason: reduce the amount of libraries loaded into the picos memory and thus improving performance
 | |
| # config: utils.Config object
 | |
| # btn_mapping: a dict containing the btn mapping for the menu operation (given to the lcdMenu object)
 | |
| # log: the utils.log function
 | |
| # lcdMenu: the lcdMenu class (not an object of that class!)
 | |
| def run(config, btn_mapping, log, lcdMenu):
 | |
|     settings_menu = lcdMenu(config.LCD, btn_mapping, scroll_direction=True, cycle=True, hide_menu_name=False, name="SETTINGS")
 | |
|     def toggle_show_welcome():
 | |
|         current_value = config.STARTUP_WELCOME_SHOW
 | |
|         config.LCD.clear()
 | |
|         config.LCD.putstr(f"Currently {'on' if current_value else 'off'}".center(16))
 | |
|         config.LCD.putstr("< keep  change >")
 | |
|         keep_btn = config.PIN_IN_BTN_1
 | |
|         change_btn = config.PIN_IN_BTN_2
 | |
|         while True:
 | |
|             if keep_btn.value() == 1:
 | |
|                 config.LCD.move_to(0,1)  # move to the second row
 | |
|                 config.LCD.putstr(f"Stay {'on' if current_value else 'off'}!".center(16))
 | |
|                 sleep(0.5)
 | |
|                 return True
 | |
|             if change_btn.value() == 1:
 | |
|                 config.STARTUP_WELCOME_SHOW = not current_value
 | |
|                 config.LCD.move_to(0,1)  # move to the second row
 | |
|                 config.LCD.putstr(f"Turned {'on' if not current_value else 'off'}!".center(16))
 | |
|                 sleep(0.5)
 | |
|                 return True
 | |
|     def welcome_cycles():
 | |
|         config.LCD.clear()
 | |
|         current_cycles = config.STARTUP_WELCOME_CYCLES
 | |
|         
 | |
|         option_down = [" ", "v"][current_cycles>1]
 | |
|         config.LCD.putstr(f"     Cycles     \n{option_down} {str(current_cycles).center(12)} ^")
 | |
|         btn_left = config.PIN_IN_BTN_1
 | |
|         btn_right = config.PIN_IN_BTN_2
 | |
|         while True:
 | |
|             if btn_left.value() == 1:
 | |
|                 sleep(0.1)  # this value is a good compromise between being able to press both buttons and a fast up/down speed
 | |
|                 if btn_right.value() == 1:
 | |
|                     config.STARTUP_WELCOME_CYCLES = current_cycles
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 
 | |
|                 current_cycles -= 1
 | |
|                 if current_cycles < 1: current_cycles = 1
 | |
|                 option_down = [" ", "v"][current_cycles>1]
 | |
|                 config.LCD.putstr(f"     Cycles     \n{option_down} {str(current_cycles).center(12)} ^")
 | |
|             if btn_right.value() == 1:
 | |
|                 sleep(0.1)
 | |
|                 if btn_left.value() == 1:
 | |
|                     config.STARTUP_WELCOME_CYCLES = current_cycles
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 current_cycles += 1
 | |
|                 option_down = [" ", "v"][current_cycles>1]
 | |
|                 config.LCD.putstr(f"     Cycles     \n{option_down} {str(current_cycles).center(12)} ^")
 | |
|     
 | |
|     # with n being the number of the timer (starting at 0)
 | |
|     def set_n_timer(n: int):
 | |
|         # a small helper function to save the value of the n'th timer...
 | |
|         # as you can't programatically access TIMER_n_DURATION
 | |
|         def set_timer_helper(n, value):
 | |
|             if n == 0:
 | |
|                 config.TIMER_1_DURATION = value
 | |
|             elif n == 1:
 | |
|                 config.TIMER_2_DURATION = value
 | |
|             elif n == 2:
 | |
|                 config.TIMER_3_DURATION = value
 | |
|             else:
 | |
|                 log(0, "There are only 3 timers at all. Trying to set the timer number {n} failed.")
 | |
|                 
 | |
|         config.LCD.clear()
 | |
|         timer_values = [config.TIMER_1_DURATION, config.TIMER_2_DURATION, config.TIMER_3_DURATION]
 | |
|         current_timer = timer_values[n]  # get the n'th timer
 | |
|         current_timer_div = lambda: divmod(current_timer, 60)
 | |
|         
 | |
| 
 | |
|         config.LCD.putstr(f"Timer {n+1}".center(16))
 | |
|         config.LCD.putstr(f"{'v' if current_timer > 1 else ' '} " + f"{current_timer_div()[0]:02d}:{current_timer_div()[1]:02d}".center(12) + " ^")
 | |
|         btn_left = config.PIN_IN_BTN_1
 | |
|         btn_right = config.PIN_IN_BTN_2
 | |
|         left_was_released = True
 | |
|         right_was_released = True
 | |
|         while True:
 | |
|             if btn_left.value() == 1:
 | |
|                 if left_was_released:
 | |
|                     time_press_start = time_ns()
 | |
|                     left_was_released = False
 | |
|                 sleep(0.1)  # this value is a good compromise between being able to press both buttons and a fast up/down speed
 | |
|                 if btn_right.value() == 1:  # exit if both btns are pressed
 | |
|                     set_timer_helper(n, current_timer)
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 # define the step width
 | |
|                 time_now = time_ns()
 | |
|                 if (time_now - time_press_start) <= 1*(10**9):  # max. 1 seconds pressed
 | |
|                     current_timer -= 1
 | |
|                 elif (time_now - time_press_start) <= 2*(10**9):  # max. 2 seconds pressed
 | |
|                     current_timer -= 5
 | |
|                 elif (time_now - time_press_start) <= 3*(10**9):  # max. 3 seconds pressed
 | |
|                     current_timer -= 10
 | |
|                 elif (time_now - time_press_start) <= 4*(10**9):  # max. 4 seconds pressed
 | |
|                     current_timer -= 30
 | |
|                 elif (time_now - time_press_start) <= 5*(10**9):  # max. 5 seconds pressed
 | |
|                     current_timer -= 60
 | |
|                 else:  # longer than 5s pressed
 | |
|                     current_timer -= 300
 | |
|                 if current_timer < 1: current_timer = 5999
 | |
|                 config.LCD.move_to(0,1)
 | |
|                 config.LCD.putstr("v " + f"{current_timer_div()[0]:02d}:{current_timer_div()[1]:02d}".center(12) + " ^")
 | |
|             else:
 | |
|                 left_was_released = True
 | |
|             if btn_right.value() == 1:
 | |
|                 if right_was_released:
 | |
|                     time_press_start = time_ns()
 | |
|                     right_was_released = False
 | |
|                 sleep(0.1)
 | |
|                 if btn_left.value() == 1:  # exit if both btns are pressed
 | |
|                     set_timer_helper(n, current_timer)
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 # define the step width
 | |
|                 time_now = time_ns()
 | |
|                 if (time_now - time_press_start) <= 1*(10**9):  # max. 1 seconds pressed
 | |
|                     current_timer += 1
 | |
|                 elif (time_now - time_press_start) <= 2*(10**9):  # max. 2 seconds pressed
 | |
|                     current_timer += 5
 | |
|                 elif (time_now - time_press_start) <= 3*(10**9):  # max. 3 seconds pressed
 | |
|                     current_timer += 10
 | |
|                 elif (time_now - time_press_start) <= 4*(10**9):  # max. 4 seconds pressed
 | |
|                     current_timer += 30
 | |
|                 elif (time_now - time_press_start) <= 5*(10**9):  # max. 5 seconds pressed
 | |
|                     current_timer += 60
 | |
|                 else:  # longer than 5s pressed
 | |
|                     current_timer += 300
 | |
|                 if current_timer > 5999: current_timer = 1
 | |
|                 config.LCD.move_to(0,1)
 | |
|                 config.LCD.putstr("v " + f"{current_timer_div()[0]:02d}:{current_timer_div()[1]:02d}".center(12) + " ^")
 | |
|             else:
 | |
|                 right_was_released = True
 | |
|     def set_log_level():
 | |
|         config.LCD.clear()
 | |
|         current_level = config.LOG_LEVEL
 | |
|         log_levels = ["WARN", "INFO", "DEBUG"]
 | |
|         
 | |
|         config.LCD.putstr(f"Log level".center(16))
 | |
|         config.LCD.putstr("v " + f"{log_levels[current_level]} ({current_level})".center(12) + " ^")  # show the log level and it's name in the second row
 | |
|         btn_left = config.PIN_IN_BTN_1
 | |
|         btn_right = config.PIN_IN_BTN_2
 | |
|         while True:
 | |
|             if btn_left.value() == 1:
 | |
|                 sleep(0.1)  # this value is a good compromise between being able to press both buttons and a fast up/down speed
 | |
|                 if btn_right.value() == 1:
 | |
|                     config.LOG_LEVEL = current_level
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 
 | |
|                 current_level -= 1
 | |
|                 if current_level < 0: current_level = 2
 | |
|                 config.LCD.move_to(0,0)
 | |
|                 config.LCD.putstr(f"Log level".center(16))
 | |
|                 config.LCD.putstr("v " + f"{log_levels[current_level]} ({current_level})".center(12) + " ^")  # show the log level and it's name in the second row
 | |
|             if btn_right.value() == 1:
 | |
|                 sleep(0.1)
 | |
|                 if btn_left.value() == 1:
 | |
|                     config.LOG_LEVEL = current_level
 | |
|                     config.LCD.move_to(0,1)  # move to the second row
 | |
|                     config.LCD.putstr(f"Saved!".center(16))  # show a little info that it is now set
 | |
|                     sleep(0.5)
 | |
|                     while btn_right.value() == 1 or btn_left.value() == 1:  # wait till both btns are released
 | |
|                         pass
 | |
|                     return True
 | |
|                 current_level += 1
 | |
|                 if current_level > 2: current_level = 0
 | |
|                 config.LCD.move_to(0,0)
 | |
|                 config.LCD.putstr(f"Log level".center(16))
 | |
|                 config.LCD.putstr("v " + f"{log_levels[current_level]} ({current_level})".center(12) + " ^")  # show the log level and it's name in the second row
 | |
|         
 | |
|     def reset():  # reset all user-settable configuration to the default values
 | |
|         config.LCD.clear()
 | |
|         config.LCD.putstr("Sure about that?")
 | |
|         config.LCD.putstr("< no       yes >")
 | |
|         no_btn = config.PIN_IN_BTN_1
 | |
|         yes_btn = config.PIN_IN_BTN_2
 | |
|         while True:
 | |
|             if no_btn.value() == 1:
 | |
|                 return None
 | |
|             if yes_btn.value() == 1:
 | |
|                 config.LCD.putstr("Resetting...".center(16))
 | |
|                 config.LCD.putstr("Welcome Screen".center(16))
 | |
|                 config.STARTUP_WELCOME_SHOW = True
 | |
|                 config.STARTUP_WELCOME_CYCLES = 1
 | |
|                 sleep(0.5)
 | |
|                 config.LCD.move_to(0,1)
 | |
|                 config.LCD.putstr("Timers".center(16))
 | |
|                 config.TIMER_1_DURATION = 60
 | |
|                 config.TIMER_2_DURATION = 2400
 | |
|                 config.TIMER_3_DURATION = 2700
 | |
|                 sleep(0.5)
 | |
|                 config.LCD.move_to(0,1)
 | |
|                 config.LCD.putstr("Logging".center(16))
 | |
|                 config.LOG_LEVEL = 1
 | |
|                 sleep(0.5)
 | |
|                 return True
 | |
|             
 | |
|     settings_programs = [("Show welcome", toggle_show_welcome),
 | |
|                          ("Welcome cycles", welcome_cycles),
 | |
|                          ("Timer 1", lambda: set_n_timer(0)),
 | |
|                          ("Timer 2", lambda: set_n_timer(1)),
 | |
|                          ("Timer 3", lambda: set_n_timer(2)),
 | |
|                          ("Log level", set_log_level),
 | |
|                          ("Reset", reset),
 | |
|                          ("Exit", settings_menu.stop)]
 | |
|     settings_menu.setup(settings_programs)  # give it the callback list
 | |
|     settings_menu.run()  # run the menu until it's closed
 | |
| 
 | |
| if __name__ == "__main__":
 | |
|     from utils import Config, log
 | |
|     from lcdMenu import lcdMenu
 | |
|     config = Config()
 | |
|     btn_mapping = {"ok_btn": config.PIN_IN_BTN_1, "next_btn": config.PIN_IN_BTN_2}  # the btn mapping for all lcdMenus
 | |
|     run(Config(), btn_mapping, log, lcdMenu) |