diff --git a/ks_includes/KlipperScreen.conf b/ks_includes/KlipperScreen.conf new file mode 100644 index 00000000..199fbfbc --- /dev/null +++ b/ks_includes/KlipperScreen.conf @@ -0,0 +1,132 @@ +[preheat PLA] +bed = 40 +extruder = 195 + +[preheat ABS] +bed = 90 +extruder = 220 + +[menu __main] + +[menu __main homing] +name: Homing +icon: home + +[menu __main preheat] +name: Preheat +icon: heat-up +panel: preheat + +[menu __main actions] +name: Actions +icon: actions + +[menu __main config] +name: Configuration +icon: control + +[menu __main print] +name: Print +icon: print +panel: print + +[menu __main homing homeall] +name: Home All +icon: home +method: printer.gcode.script +params: {"script":"G28"} + +[menu __main homing homex] +name: Home X +icon: home +method: printer.gcode.script +params: {"script":"G28 X"} + +[menu __main homing homey] +name: Home Y +icon: home +method: printer.gcode.script +params: {"script":"G28 Y"} + +[menu __main homing homez] +name: Home Z +icon: home +method: printer.gcode.script +params: {"script":"G28 Z"} + +[menu __main homing homexy] +name: Home XY +icon: home +method: printer.gcode.script +params: {"script":"G28 X Y"} + +[menu __main actions move] +name: Move +icon: heat-up +panel: move + +[menu __main actions extrude] +name: Extrude +icon: filament +panel: extrude + +[menu __main actions fan] +name: Fan +icon: fan +panel: fan + +[menu __main actions temperature] +name: Temperature +icon: heat-up +panel: temperature + +[menu __main actions disablemotors] +name: Disable Motors +icon: motor-off +method: printer.gcode.script +params: {"script":"M18"} + +[menu __main config bedlevel] +name: Bed Level +icon: bed-level +panel: bed_level + +[menu __main config zoffset] +name: Z Calibrate +icon: z-offset-increase +panel: zcalibrate + +[menu __main config network] +name: Network +icon: network +panel: network + +[menu __main config system] +name: System +icon: info +panel: system + +[menu __print temperature] +name: Temperature +icon: heat-up +panel: temperature + +[menu __print tuning] +name: Fine Tuning +icon: fan +panel: finetune + +[menu __print network] +name: Network +icon: network +panel: network + +[menu __print system] +name: System +icon: info +panel: system + +[menu __print extrude] +name: Extrude +icon: filament +panel: extrude diff --git a/ks_includes/config.py b/ks_includes/config.py new file mode 100644 index 00000000..356835b2 --- /dev/null +++ b/ks_includes/config.py @@ -0,0 +1,115 @@ +import configparser +import os +import logging +import json + +from io import StringIO + +from os import path + +logger = logging.getLogger("KlipperScreen.config") + +class ConfigError(Exception): + pass + +class KlipperScreenConfig: + config = None + + def __init__(self): + self.config = configparser.ConfigParser() + self.config_path = self.get_config_file_location() + + try: + self.config.read(self.config_path) + except KeyError: + raise ConfigError(f"Error reading config: {self.config_path}") + + self.log_config(self.config) + + self.get_menu_items("__main") + #self.build_main_menu(self.config) + + + def get_config_file_location(self): + conf_name = "KlipperScreen.conf" + + file = "%s/%s" % (os.getenv("HOME"), conf_name) + if not path.exists(file): + file = "%s/%s" % (os.getcwd(), conf_name) + if not path.exists(file): + file = "%s/ks_includes/%s" % (os.getcwd(), conf_name) + + logger.info("Found configuration file at: %s" % file) + return file + + def get_menu_items(self, menu="__main", subsection=""): + if subsection != "": + subsection = subsection + " " + index = "menu %s %s" % (menu, subsection) + logger.debug("Getting menu items for: %s" % index) + items = [i[len(index):] for i in self.config.sections() if i.startswith(index)] + menu_items = [] + for item in items: + split = item.split() + if len(split) == 1: + menu_items.append(self._build_menu_item(menu, index + item)) + + return menu_items + + def get_preheat_options(self): + index = "preheat " + items = [i[len(index):] for i in self.config.sections() if i.startswith(index)] + logger.debug("Items: %s" % items) + + preheat_options = {} + for item in items: + preheat_options[item] = self._build_preheat_item(index + item) + + return preheat_options + + + def log_config(self, config): + lines = [ + " " + "===== Config File =====", + self._build_config_string(config), + "=======================" + ] + logger.info("\n".join(lines)) + + def _build_config_string(self, config): + sfile = StringIO() + config.write(sfile) + sfile.seek(0) + return sfile.read().strip() + + + + def _build_menu_item(self, menu, name): + if name not in self.config: + return False + cfg = self.config[name] + item = { + "name": cfg.get("name"), + "icon": cfg.get("icon"), + "panel": cfg.get("panel", False), + "method": cfg.get("method", False), + } + + try: + item["params"] = json.loads(cfg.get("params", "{}")) + except: + logger.debug("Unable to parse parameters for [%s]" % name) + item["params"] = {} + + return {name[(len(menu) + 6):]: item} + + def _build_preheat_item(self, name): + if name not in self.config: + return False + cfg = self.config[name] + item = { + "extruder": cfg.getint("extruder", 0), + "bed": cfg.getint("bed", 0) + } + return item diff --git a/panels/menu.py b/panels/menu.py index 0e1f03d3..ececa57a 100644 --- a/panels/menu.py +++ b/panels/menu.py @@ -32,19 +32,24 @@ class MenuPanel(ScreenPanel): col = i % columns row = int(i/columns) width = 1 + if expandLast == True and i+1 == l and l%2 == 1: width = 2 - b = KlippyGtk.ButtonImage( - items[i]['icon'], items[i]['name'], "color"+str((i%4)+1) - ) - if "panel" in items[i]: - b.connect("clicked", self.menu_item_clicked, items[i]['panel'], items[i]) - elif "items" in items[i]: - b.connect("clicked", self._screen._go_to_submenu, items[i]['name']) - elif "method" in items[i]: - params = items[i]['params'] if "params" in items[i] else {} - b.connect("clicked", self._screen._send_action, items[i]['method'], params) + key = list(items[i])[0] + logger.debug("Key: %s" % key) + item = items[i][key] + b = KlippyGtk.ButtonImage( + item['icon'], item['name'], "color"+str((i%4)+1) + ) + logger.debug("Item: %s" % item) + if item['panel'] != False: + b.connect("clicked", self.menu_item_clicked, item['panel'], item) + elif item['method'] != False: + params = item['params'] if item['params'] != False else {} + b.connect("clicked", self._screen._send_action, item['method'], params) + else: + b.connect("clicked", self._screen._go_to_submenu, key) grid.attach(b, col, row, width, 1) diff --git a/panels/preheat.py b/panels/preheat.py index 16c807b5..39945d1e 100644 --- a/panels/preheat.py +++ b/panels/preheat.py @@ -13,7 +13,8 @@ class PreheatPanel(ScreenPanel): active_heaters = [] def initialize(self, panel_name): - self.preheat_options = self._screen._config['preheat_options'] + self.preheat_options = self._screen._config.get_preheat_options() + logger.debug("Preheat options: %s" % self.preheat_options) grid = KlippyGtk.HomogeneousGrid() @@ -99,10 +100,10 @@ class PreheatPanel(ScreenPanel): self._screen._ws.klippy.set_bed_temp(self.preheat_options[setting]["bed"]) self._printer.set_dev_stat(heater,"target", int(self.preheat_options[setting]["bed"])) else: - print ("Setting %s to %d" % (heater, self.preheat_options[setting]['tool'])) + print ("Setting %s to %d" % (heater, self.preheat_options[setting]['extruder'])) self._screen._ws.klippy.set_tool_temp(self._printer.get_tool_number(heater), - self.preheat_options[setting]["tool"]) - self._printer.set_dev_stat(heater,"target", int(self.preheat_options[setting]["tool"])) + self.preheat_options[setting]["extruder"]) + self._printer.set_dev_stat(heater,"target", int(self.preheat_options[setting]["extruder"])) def process_update(self, data): self.update_temp("heater_bed", diff --git a/screen.py b/screen.py index 26313ca9..e56a3735 100644 --- a/screen.py +++ b/screen.py @@ -22,6 +22,8 @@ from files import KlippyFiles from KlippyGtk import KlippyGtk from printer import Printer +from ks_includes.config import KlipperScreenConfig + # Do this better in the future from panels.screen_panel import * from panels.bed_level import * @@ -76,7 +78,7 @@ class KlipperScreen(Gtk.Window): printer = None def __init__(self): - self.read_config() + self._config = KlipperScreenConfig() self.init_style() self.printer = Printer({ 'configfile': { @@ -240,19 +242,6 @@ class KlipperScreen(Gtk.Window): def error_modal_response(self, widget, response_id): widget.destroy() - def read_config (self): - try: - with open(config) as config_file: - self._config = json.load(config_file) - lines = [ - "===== Config File =====", - json.dumps(self._config, indent=2), - "=======================", - ] - logger.info("\n".join(lines)) - except: - logger.exception("Error reading configuration file") - def init_style(self): style_provider = Gtk.CssProvider() @@ -271,15 +260,19 @@ class KlipperScreen(Gtk.Window): # Find current menu item panels = list(self._cur_panels) if "job_status" not in self._cur_panels: - cur_item = self._find_current_menu_item(name, self._config['mainmenu'], panels.pop(0)) - menu = cur_item['items'] + menu = "__main" else: - menu = self._config['printmenu'] + menu = "__print" logger.info("#### Menu " + str(menu)) #self.show_panel("_".join(self._cur_panels) + '_' + name, "menu", 1, False, menu=menu) - self.show_panel(self._cur_panels[-1] + '_' + name, "menu", 1, False, items=menu) + menuitems = self._config.get_menu_items(menu, name) + if len(menuitems) == 0: + logger.info("No items in menu, returning.") + return + + self.show_panel(self._cur_panels[-1] + '_' + name, "menu", 1, False, items=menuitems) return grid = self.arrangeMenuItems(menu, 4) @@ -293,14 +286,6 @@ class KlipperScreen(Gtk.Window): self.add(self.panels[cur_item['name']]) self.show_all() - - - def _find_current_menu_item(self, menu, items, names): - for item in items: - if item['name'] == menu: - return item - #TODO: Add error check - def _remove_all_panels(self): while len(self._cur_panels) > 0: self._remove_current_panel() @@ -442,7 +427,7 @@ class KlipperScreen(Gtk.Window): return self.files.add_timeout() - self.show_panel('main_panel', "MainPanel", 2, items=self._config['mainmenu'], extrudercount=self.printer.get_extruder_count()) + self.show_panel('main_panel', "MainPanel", 2, items=self._config.get_menu_items("__main"), extrudercount=self.printer.get_extruder_count()) def printer_printing(self): self.ws_subscribe()