home · contact · privacy
More Events refactoring. master
authorChristian Heller <c.heller@plomlompom.de>
Mon, 4 Aug 2025 14:57:15 +0000 (16:57 +0200)
committerChristian Heller <c.heller@plomlompom.de>
Mon, 4 Aug 2025 14:57:15 +0000 (16:57 +0200)
ircplom/client.py
ircplom/events.py
ircplom/tui_base.py

index c95c99d403ba79b03a35c851a7ad76012684ad87..81c53846160caa3d57f2010fec5241b7d6e663ee 100644 (file)
@@ -31,15 +31,6 @@ class ClientIdMixin:
 class ClientEvent(AffectiveEvent, ClientIdMixin):
     'To affect Client identified by ClientIdMixin.'
 
 class ClientEvent(AffectiveEvent, ClientIdMixin):
     'To affect Client identified by ClientIdMixin.'
 
-    @classmethod
-    def make_subtype(cls, method_to_call: str, **kwargs
-                     ) -> type['ClientEvent']:
-        'Return subclass whose .affect calls method_to_call on target, kwargs.'
-        class _AdaptedEvent(ClientEvent):
-            def affect(self, target) -> None:
-                getattr(target, method_to_call)(**kwargs)
-        return _AdaptedEvent
-
 
 class _IrcConnection(BaseIrcConnection):
 
 
 class _IrcConnection(BaseIrcConnection):
 
@@ -49,6 +40,7 @@ class _IrcConnection(BaseIrcConnection):
         super().__init__(**kwargs)
 
     def _make_recv_event(self, msg: IrcMessage) -> ClientEvent:
         super().__init__(**kwargs)
 
     def _make_recv_event(self, msg: IrcMessage) -> ClientEvent:
+        # pylint: disable=unexpected-keyword-arg  # confused by client_id=
         return ClientEvent.make_subtype(method_to_call='handle_msg', msg=msg)(
                 client_id=self.client_id)
 
         return ClientEvent.make_subtype(method_to_call='handle_msg', msg=msg)(
                 client_id=self.client_id)
 
index 07c82bcd77277b5ed750a22f1845eb9fc150982e..4af5f021a4f5e87031117c99eb8dbdfe036d2783 100644 (file)
@@ -22,6 +22,14 @@ class AffectiveEvent(Event, ABC):
     def affect(self, target: Any) -> None:
         'To be run by main loop on target.'
 
     def affect(self, target: Any) -> None:
         'To be run by main loop on target.'
 
+    @classmethod
+    def make_subtype(cls: Any, method_to_call: str, **kwargs):
+        'Return subclass whose .affect calls method_to_call on target, kwargs.'
+        class _AdaptedEvent(cls):
+            def affect(self, target) -> None:
+                getattr(target, method_to_call)(**kwargs)
+        return _AdaptedEvent
+
 
 @dataclass
 class PayloadMixin:
 
 @dataclass
 class PayloadMixin:
index cf9513270436550973cb59119405ce8aac95975e..d3a0379a022440daa1a1a933a58ae8958a8dc640 100644 (file)
@@ -10,9 +10,7 @@ from typing import Callable, Generator, Iterator, NamedTuple, Optional
 # requirements.txt
 from blessed import Terminal as BlessedTerminal
 # ourselves
 # requirements.txt
 from blessed import Terminal as BlessedTerminal
 # ourselves
-from ircplom.events import (
-        AffectiveEvent, Logger, Loop, PayloadMixin, QueueMixin, QuitEvent)
-# from ircplom.irc_conn import IrcMessage
+from ircplom.events import AffectiveEvent, Logger, Loop, QueueMixin, QuitEvent
 
 _MIN_HEIGHT = 4
 _MIN_WIDTH = 32
 
 _MIN_HEIGHT = 4
 _MIN_WIDTH = 32
@@ -349,39 +347,6 @@ class TuiEvent(AffectiveEvent):
     'To affect TUI.'
 
 
     'To affect TUI.'
 
 
-@dataclass
-class _KeyboardEvent(TuiEvent, PayloadMixin):
-    payload: str
-
-    def affect(self, target: 'BaseTui') -> None:
-        if self.payload[0] == _CHAR_RESIZE:
-            target.set_screen()
-            return
-        if self.payload in _KEYBINDINGS:
-            cmd_data = _KEYBINDINGS[self.payload]
-            cmd = target.cmd_name_to_cmd(cmd_data[0])
-            if cmd:
-                cmd(*cmd_data[1:])
-        elif self.payload.startswith(_B64_PREFIX):
-            encoded = self.payload[len(_B64_PREFIX):]
-            to_paste = ''
-            for i, c in enumerate(b64decode(encoded).decode('utf-8')):
-                if i > 512:
-                    break
-                if c.isprintable():
-                    to_paste += c
-                elif c.isspace():
-                    to_paste += ' '
-                else:
-                    to_paste += '#'
-            target.window.prompt.insert(to_paste)
-        elif len(self.payload) == 1:
-            target.window.prompt.insert(self.payload)
-        else:
-            target.log.alert(f'unknown keyboard input: {self.payload}')
-        target.redraw_affected()
-
-
 class BaseTui(QueueMixin):
     'Base for graphical user interface elements.'
 
 class BaseTui(QueueMixin):
     'Base for graphical user interface elements.'
 
@@ -434,6 +399,35 @@ class BaseTui(QueueMixin):
         self._window_idx = idx
         self.window.draw()
 
         self._window_idx = idx
         self.window.draw()
 
+    def handle_keyboard_event(self, typed_in: str) -> None:
+        'Translate keyboard input into appropriate actions.'
+        if typed_in[0] == _CHAR_RESIZE:
+            self.set_screen()
+            return
+        if typed_in in _KEYBINDINGS:
+            cmd_data = _KEYBINDINGS[typed_in]
+            cmd = self.cmd_name_to_cmd(cmd_data[0])
+            if cmd:
+                cmd(*cmd_data[1:])
+        elif typed_in.startswith(_B64_PREFIX):
+            encoded = typed_in[len(_B64_PREFIX):]
+            to_paste = ''
+            for i, c in enumerate(b64decode(encoded).decode('utf-8')):
+                if i > 512:
+                    break
+                if c.isprintable():
+                    to_paste += c
+                elif c.isspace():
+                    to_paste += ' '
+                else:
+                    to_paste += '#'
+            self.window.prompt.insert(to_paste)
+        elif len(typed_in) == 1:
+            self.window.prompt.insert(typed_in)
+        else:
+            self.log.alert(f'unknown keyboard input: {typed_in}')
+        self.redraw_affected()
+
     def cmd__prompt_enter(self) -> None:
         'Get prompt content from .window.prompt.enter, parse to & run command.'
         to_parse = self.window.prompt.enter()
     def cmd__prompt_enter(self) -> None:
         'Get prompt content from .window.prompt.enter, parse to & run command.'
         to_parse = self.window.prompt.enter()
@@ -559,7 +553,7 @@ class Terminal(QueueMixin):
         print(msg, end='')
         self._cursor_yx = _YX(self._cursor_yx.y, end_x)
 
         print(msg, end='')
         self._cursor_yx = _YX(self._cursor_yx.y, end_x)
 
-    def _get_keypresses(self) -> Iterator[Optional[_KeyboardEvent]]:
+    def _get_keypresses(self) -> Iterator[Optional[TuiEvent]]:
         '''Loop through keypresses from terminal, expand blessed's handling.
 
         Explicitly collect KEY_ESCAPE-modified key sequences, and recognize
         '''Loop through keypresses from terminal, expand blessed's handling.
 
         Explicitly collect KEY_ESCAPE-modified key sequences, and recognize
@@ -599,4 +593,6 @@ class Terminal(QueueMixin):
                             to_yield += c
                 else:
                     to_yield = 'esc:' + ':'.join([str(int(b)) for b in chars])
                             to_yield += c
                 else:
                     to_yield = 'esc:' + ':'.join([str(int(b)) for b in chars])
-            yield _KeyboardEvent(to_yield) if to_yield else None
+            yield (TuiEvent.make_subtype('handle_keyboard_event',
+                                         typed_in=to_yield)() if to_yield
+                   else None)