further plugin work, refactoring
This commit is contained in:
parent
a863dbc586
commit
95c6f79627
|
@ -1,5 +1,5 @@
|
||||||
# Python imports
|
# Python imports
|
||||||
import sys, traceback, threading, inspect, os, time
|
import sys, threading, subprocess, time
|
||||||
|
|
||||||
# Gtk imports
|
# Gtk imports
|
||||||
import gi
|
import gi
|
||||||
|
@ -11,26 +11,42 @@ from gi.repository import Gtk
|
||||||
|
|
||||||
def threaded(fn):
|
def threaded(fn):
|
||||||
def wrapper(*args, **kwargs):
|
def wrapper(*args, **kwargs):
|
||||||
threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=True).start()
|
threading.Thread(target=fn, args=args, kwargs=kwargs, daemon=False).start()
|
||||||
return wrapper
|
return wrapper
|
||||||
|
|
||||||
|
|
||||||
class Main:
|
class Main:
|
||||||
def __init__(self, socket_id, event_system):
|
def __init__(self, socket_id, event_system):
|
||||||
self._socket_id = socket_id
|
self._plugin_name = "Example Plugin"
|
||||||
self._event_system = event_system
|
self._event_system = event_system
|
||||||
|
self._socket_id = socket_id
|
||||||
self._gtk_plug = Gtk.Plug.new(self._socket_id)
|
self._gtk_plug = Gtk.Plug.new(self._socket_id)
|
||||||
|
|
||||||
button = Gtk.Button(label="Click Me!")
|
button = Gtk.Button(label="Click Me!")
|
||||||
|
self._message = None
|
||||||
|
self._time_out = 5
|
||||||
|
|
||||||
button.connect("button-release-event", self._do_action)
|
button.connect("button-release-event", self._do_action)
|
||||||
self._gtk_plug.add(button)
|
self._gtk_plug.add(button)
|
||||||
self._gtk_plug.show_all()
|
self._gtk_plug.show_all()
|
||||||
|
|
||||||
|
|
||||||
|
@threaded
|
||||||
def _do_action(self, widget=None, eve=None):
|
def _do_action(self, widget=None, eve=None):
|
||||||
message = "Hello, World!"
|
message = "Hello, World!"
|
||||||
self._event_system.push_gui_event(["some_type", "display_message", ("warning", message, None)])
|
self._event_system.push_gui_event(["some_type", "display_message", ("warning", message, None)])
|
||||||
|
|
||||||
|
|
||||||
|
def set_message(self, data):
|
||||||
|
self._message = data
|
||||||
|
|
||||||
|
def get_plugin_name(self):
|
||||||
|
return self._plugin_name
|
||||||
|
|
||||||
def get_socket_id(self):
|
def get_socket_id(self):
|
||||||
return self._socket_id
|
return self._socket_id
|
||||||
|
|
||||||
|
def _run_timeout(self):
|
||||||
|
timeout = 0
|
||||||
|
while not self._message and timeout < self._time_out:
|
||||||
|
time.sleep(1)
|
||||||
|
timeout += 1
|
||||||
|
|
|
@ -13,13 +13,13 @@ class Builtins(IPCServerMixin):
|
||||||
"""Docstring for __builtins__ extender"""
|
"""Docstring for __builtins__ extender"""
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
# NOTE: The format used is list of [type, target, data] Where:
|
# NOTE: The format used is list of [type, target, (data,)] Where:
|
||||||
# type is useful context for control flow,
|
# type is useful context for control flow,
|
||||||
# target is the method to call,
|
# target is the method to call,
|
||||||
# data is the method parameters to give
|
# data is the method parameters to give
|
||||||
# Where data may be any kind of data
|
# Where data may be any kind of data
|
||||||
self._gui_events = []
|
self._gui_events = []
|
||||||
self._fm_events = []
|
self._module_events = []
|
||||||
self.is_ipc_alive = False
|
self.is_ipc_alive = False
|
||||||
self.ipc_authkey = b'solarfm-ipc'
|
self.ipc_authkey = b'solarfm-ipc'
|
||||||
self.ipc_address = '127.0.0.1'
|
self.ipc_address = '127.0.0.1'
|
||||||
|
@ -33,9 +33,9 @@ class Builtins(IPCServerMixin):
|
||||||
return self._gui_events.pop(0)
|
return self._gui_events.pop(0)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
def _pop_fm_event(self):
|
def _pop_module_event(self):
|
||||||
if len(self._fm_events) > 0:
|
if len(self._module_events) > 0:
|
||||||
return self._fm_events.pop(0)
|
return self._module_events.pop(0)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
|
||||||
|
@ -44,26 +44,26 @@ class Builtins(IPCServerMixin):
|
||||||
self._gui_events.append(event)
|
self._gui_events.append(event)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
raise Exception("Invald event format! Please do: [type, target, data]")
|
raise Exception("Invald event format! Please do: [type, target, (data,)]")
|
||||||
|
|
||||||
def push_fm_event(self, event):
|
def push_module_event(self, event):
|
||||||
if len(event) == 3:
|
if len(event) == 3:
|
||||||
self._fm_events.append(event)
|
self._module_events.append(event)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
raise Exception("Invald event format! Please do: [type, target, data]")
|
raise Exception("Invald event format! Please do: [type, target, (data,)]")
|
||||||
|
|
||||||
def read_gui_event(self):
|
def read_gui_event(self):
|
||||||
return self._gui_events[0]
|
return self._gui_events[0]
|
||||||
|
|
||||||
def read_fm_event(self):
|
def read_module_event(self):
|
||||||
return self._fm_events[0]
|
return self._module_events[0]
|
||||||
|
|
||||||
def consume_gui_event(self):
|
def consume_gui_event(self):
|
||||||
return self._pop_gui_event()
|
return self._pop_gui_event()
|
||||||
|
|
||||||
def consume_fm_event(self):
|
def consume_module_event(self):
|
||||||
return self._pop_fm_event()
|
return self._pop_module_event()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -57,11 +57,20 @@ class Controller(UIMixin, KeyboardSignalsMixin, IPCSignalsMixin, Controller_Data
|
||||||
if event:
|
if event:
|
||||||
try:
|
try:
|
||||||
type, target, data = event
|
type, target, data = event
|
||||||
|
if type:
|
||||||
|
method = getattr(self.__class__, "handle_gui_event_and_set_message")
|
||||||
|
GLib.idle_add(method, *(self, type, target, data))
|
||||||
|
else:
|
||||||
method = getattr(self.__class__, target)
|
method = getattr(self.__class__, target)
|
||||||
GLib.idle_add(method, *(self, *data,))
|
GLib.idle_add(method, *(self, *data,))
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(repr(e))
|
print(repr(e))
|
||||||
|
|
||||||
|
def handle_gui_event_and_set_message(self, type, target, parameters):
|
||||||
|
method = getattr(self.__class__, f"{target}")
|
||||||
|
data = method(*(self, *parameters))
|
||||||
|
self.plugins.set_message_on_plugin(type, data)
|
||||||
|
|
||||||
def custom_except_hook(self, exctype, value, _traceback):
|
def custom_except_hook(self, exctype, value, _traceback):
|
||||||
trace = ''.join(traceback.format_tb(_traceback))
|
trace = ''.join(traceback.format_tb(_traceback))
|
||||||
data = f"Exectype: {exctype} <--> Value: {value}\n\n{trace}\n\n\n\n"
|
data = f"Exectype: {exctype} <--> Value: {value}\n\n{trace}\n\n\n\n"
|
||||||
|
|
|
@ -10,6 +10,12 @@ from gi.repository import Gtk, Gio
|
||||||
# Application imports
|
# Application imports
|
||||||
|
|
||||||
|
|
||||||
|
class Plugin:
|
||||||
|
name = None
|
||||||
|
module = None
|
||||||
|
gtk_socket_id = None
|
||||||
|
gtk_socket = None
|
||||||
|
reference = None
|
||||||
|
|
||||||
|
|
||||||
class Plugins:
|
class Plugins:
|
||||||
|
@ -19,16 +25,9 @@ class Plugins:
|
||||||
self._plugin_list_widget = self._settings.get_builder().get_object("plugin_list")
|
self._plugin_list_widget = self._settings.get_builder().get_object("plugin_list")
|
||||||
self._plugin_list_socket = self._settings.get_builder().get_object("plugin_socket")
|
self._plugin_list_socket = self._settings.get_builder().get_object("plugin_socket")
|
||||||
self._plugins_path = self._settings.get_plugins_path()
|
self._plugins_path = self._settings.get_plugins_path()
|
||||||
self._gtk_socket = Gtk.Socket().new()
|
|
||||||
self._plugins_dir_watcher = None
|
self._plugins_dir_watcher = None
|
||||||
self._plugin_collection = []
|
self._plugin_collection = []
|
||||||
|
|
||||||
self._plugin_list_socket.add(self._gtk_socket)
|
|
||||||
|
|
||||||
# NOTE: Must get ID after adding socket to window. Else issues....
|
|
||||||
self._gtk_socket_id = self._gtk_socket.get_id()
|
|
||||||
self._plugin_list_widget.show_all()
|
|
||||||
|
|
||||||
|
|
||||||
def launch_plugins(self):
|
def launch_plugins(self):
|
||||||
self._set_plugins_watcher()
|
self._set_plugins_watcher()
|
||||||
|
@ -45,17 +44,36 @@ class Plugins:
|
||||||
Gio.FileMonitorEvent.MOVED_OUT]:
|
Gio.FileMonitorEvent.MOVED_OUT]:
|
||||||
self.reload_plugins(file)
|
self.reload_plugins(file)
|
||||||
|
|
||||||
|
# @threaded
|
||||||
def load_plugins(self, file=None):
|
def load_plugins(self, file=None):
|
||||||
print(f"Loading plugins...")
|
print(f"Loading plugins...")
|
||||||
for file in os.listdir(self._plugins_path):
|
for file in os.listdir(self._plugins_path):
|
||||||
|
try:
|
||||||
path = join(self._plugins_path, file)
|
path = join(self._plugins_path, file)
|
||||||
if isdir(path):
|
if isdir(path):
|
||||||
|
gtk_socket = Gtk.Socket().new()
|
||||||
|
self._plugin_list_socket.add(gtk_socket)
|
||||||
|
# NOTE: Must get ID after adding socket to window. Else issues....
|
||||||
|
gtk_socket_id = gtk_socket.get_id()
|
||||||
|
|
||||||
spec = importlib.util.spec_from_file_location(file, join(path, "__main__.py"))
|
spec = importlib.util.spec_from_file_location(file, join(path, "__main__.py"))
|
||||||
module = importlib.util.module_from_spec(spec)
|
module = importlib.util.module_from_spec(spec)
|
||||||
|
|
||||||
spec.loader.exec_module(module)
|
spec.loader.exec_module(module)
|
||||||
plugin = module.Main(self._gtk_socket_id, event_system)
|
|
||||||
self._plugin_collection.append([file, plugin])
|
ref = module.Main(gtk_socket_id, event_system)
|
||||||
|
plugin = Plugin()
|
||||||
|
plugin.name = ref.get_plugin_name()
|
||||||
|
plugin.module = path
|
||||||
|
plugin.gtk_socket_id = gtk_socket_id
|
||||||
|
plugin.gtk_socket = gtk_socket
|
||||||
|
plugin.reference = ref
|
||||||
|
|
||||||
|
self._plugin_collection.append(plugin)
|
||||||
|
gtk_socket.show_all()
|
||||||
|
except Exception as e:
|
||||||
|
print("Malformed plugin! Not loading!")
|
||||||
|
print(repr(e))
|
||||||
|
|
||||||
|
|
||||||
def reload_plugins(self, file=None):
|
def reload_plugins(self, file=None):
|
||||||
print(f"Reloading plugins...")
|
print(f"Reloading plugins...")
|
||||||
|
@ -64,3 +82,10 @@ class Plugins:
|
||||||
# for dir in self._plugin_collection:
|
# for dir in self._plugin_collection:
|
||||||
# if not os.path.isdir(os.path.join(self._plugins_path, dir)):
|
# if not os.path.isdir(os.path.join(self._plugins_path, dir)):
|
||||||
# to_unload.append(dir)
|
# to_unload.append(dir)
|
||||||
|
|
||||||
|
def set_message_on_plugin(self, type, data):
|
||||||
|
print("Trying to send message to plugin...")
|
||||||
|
for plugin in self._plugin_collection:
|
||||||
|
if type in plugin.name:
|
||||||
|
print('Found plugin; posting message...')
|
||||||
|
plugin.reference.set_message(data)
|
||||||
|
|
|
@ -32,7 +32,7 @@ class WindowController:
|
||||||
def fm_event_observer(self):
|
def fm_event_observer(self):
|
||||||
while True:
|
while True:
|
||||||
time.sleep(event_sleep_time)
|
time.sleep(event_sleep_time)
|
||||||
event = event_system.consume_fm_event()
|
event = event_system.consume_module_event()
|
||||||
if event:
|
if event:
|
||||||
print(event)
|
print(event)
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue