From f2b300d9e01547628cd409f9666d457b5ea045ee Mon Sep 17 00:00:00 2001 From: Sébastien Dailly Date: Mon, 7 Jul 2025 08:31:38 +0200 Subject: Added error message --- configuration.py | 13 +++++++++++-- interfaces/message.py | 19 ++++++++++++++++++- macropad.pyw | 26 +++++++++++++++++++------- 3 files changed, 48 insertions(+), 10 deletions(-) diff --git a/configuration.py b/configuration.py index fceef14..78cce27 100644 --- a/configuration.py +++ b/configuration.py @@ -1,7 +1,15 @@ +""" The configuration from the user. +""" + from collections import OrderedDict from os import path import json +from zope import component +from interfaces.message import Error class Mapping(): + """Represent the configuration. This class is provided as an utility and is + used in the IDesktop interfaces. + """ def __init__(self, configuration): self.init_mapping = configuration["mapping"] @@ -10,7 +18,7 @@ class Mapping(): for key in tmp_mapping.keys() : json_file = self.init_mapping[key] if not path.exists(json_file): - print("The file '%s' does not exists" % json_file) + component.handle(Error(f"The file '{json_file}' does not exists")) continue with open(json_file, "r") as file: json_data = file.read() @@ -27,6 +35,8 @@ class Mapping(): del self.mapping[key] def get(self, key, default): + """ This function return the mapping associated with the given key. + """ return self.mapping.get(key, default) def __getitem__(self, key): @@ -44,4 +54,3 @@ class Mapping(): """ Implement the keys method from the dictionnary """ return self.mapping.keys() - diff --git a/interfaces/message.py b/interfaces/message.py index 23ce2ec..bf05bef 100755 --- a/interfaces/message.py +++ b/interfaces/message.py @@ -1,14 +1,31 @@ +"""Messages sent to the user. +""" + from zope import interface from zope.interface import Attribute class IMessage(interface.Interface): + """Interface for all the user messages. + """ content = Attribute("""The text message to log""") + level = Attribute("""Level of the message, 0 is high level and 10 is the lower""") class ISocketMessage(interface.Interface): + """Message to sent to the endpoint.""" content = Attribute("""Content to send""") @interface.implementer(IMessage) -class Debug(object): +class Debug(): + """Send a message with a low level""" + + def __init__(self, message): + self.content = message + self.level = 10 + +@interface.implementer(IMessage) +class Error(): + """Send a message with a high level""" def __init__(self, message): self.content = message + self.level = 0 diff --git a/macropad.pyw b/macropad.pyw index 6e4f922..a175931 100755 --- a/macropad.pyw +++ b/macropad.pyw @@ -15,7 +15,7 @@ from PIL import Image from zope import component import interfaces from interfaces import endpoint -from interfaces.message import IMessage, Debug +from interfaces.message import IMessage, Debug, Error import consumer from configuration import Mapping @@ -27,8 +27,6 @@ config_file = path.join(script_path, "config.ini") config = configparser.ConfigParser(delimiters="=") config.read(config_file) -mapping = Mapping(config) -component.provideUtility(mapping, interfaces.configuration.IConfiguration) # # Guess the platform and the load the corresponding event listener @@ -64,6 +62,7 @@ handler.start() class Icon(): + """Icon displayed in the notification bar.""" def __init__(self, image): menu=( @@ -101,12 +100,15 @@ class Icon(): mapping.reset() class Application(): + """ The main application. + """ def __init__(self): # Override the default function called when exception are reported tk.Tk.report_callback_exception = self.report_callback_exception self.window = tk.Tk() self.text = Text(self.window, height=8) + self.text.tag_config("error", background="red", foreground="white") ## State of the #pplication self.running = True self.visible = False @@ -137,15 +139,18 @@ class Application(): """ Launch the thread listening events from the desktop """ component.handle(Debug(platform)) + listener = None if platform == "win32": import win32 listener = win32.Listener(mapping) elif platform == 'linux': import xlib listener = xlib.Listener(mapping) - component.handle(Debug("Starting xlib")) - component.provideUtility(listener, interfaces.desktopEvent.IDesktop) - listener.start() + if listener is not None: + component.provideUtility(listener, interfaces.desktopEvent.IDesktop) + listener.start() + else: + component.handle(Error("Unsupported system %s" % platform)) def report_callback_exception(self, exc, val, tb): """ Handle exception reported inside the Tk application. @@ -191,6 +196,9 @@ class Application(): self.text.insert("1.0", "\n") self.text.insert("1.0", message.content) self.text.delete("200.0", "end") + if message.level == 0: + self.text.tag_add("error", "1.0", "1.end") + self.icon.show_hide.set() except Exception as e: print(e) @@ -212,6 +220,8 @@ if __name__ == '__main__': # Start the main application, Initializing the message listener before # listening desktop events app = Application() + mapping = Mapping(config) + component.provideUtility(mapping, interfaces.configuration.IConfiguration) app.connect_desktop() # Initialize the main loop @@ -222,4 +232,6 @@ if __name__ == '__main__': app.running = False app.window.destroy() app.icon.quit() - component.queryUtility(interfaces.desktopEvent.IDesktop).stop() + desktop = component.queryUtility(interfaces.desktopEvent.IDesktop) + if desktop is not None: + desktop.stop() -- cgit v1.2.3