From a0a40e9259b9e8be4e677c8c29dfdfb89eb81ce8 Mon Sep 17 00:00:00 2001 From: Jonas Bernard Date: Sat, 24 Apr 2021 04:19:39 +0200 Subject: Progress at night --- txtgameengine/__main__.py | 5 ++++ txtgameengine/app.py | 4 +++- txtgameengine/input/__init__.py | 0 txtgameengine/input/callbacks.py | 31 ++++++++++++++++++++++++ txtgameengine/input/keyboard.py | 52 ++++++++++++++++++++++++++++++++++++++++ txtgameengine/platform.py | 7 ++++++ txtgameengine/scenes.py | 2 +- 7 files changed, 99 insertions(+), 2 deletions(-) create mode 100644 txtgameengine/input/__init__.py create mode 100644 txtgameengine/input/callbacks.py create mode 100644 txtgameengine/input/keyboard.py diff --git a/txtgameengine/__main__.py b/txtgameengine/__main__.py index a56571e..71085e1 100644 --- a/txtgameengine/__main__.py +++ b/txtgameengine/__main__.py @@ -4,6 +4,7 @@ from .scenes import SceneTxtGameApp, Scene from pathlib import Path from .shaders import TextureShader from .twod.textures import Texture, TEXTURE_FOLDER +from.input.keyboard import ModKey, KeyboardEvent shader_path = Path(__file__).parent / 'shaders' @@ -75,9 +76,13 @@ class TestApp(SceneTxtGameApp): def init(self): super().init() self.render.setup_vertex_arrays() + self.handler.register_keyboard_callback(self.handler.keyboard_callback() + .with_mod_key(ModKey.CONTROL) + .build(lambda key_event: print(key_event.keycode))) # self.platform.check_debug() + if __name__ == '__main__': a = TestApp((640, 480), "OpenGL window") a.start() diff --git a/txtgameengine/app.py b/txtgameengine/app.py index 8206ef4..a596f22 100644 --- a/txtgameengine/app.py +++ b/txtgameengine/app.py @@ -1,4 +1,5 @@ from pathlib import Path +from .input.callbacks import CallbackHandler EPSILON = 1.e-10 builtin_resource_path = Path(__file__).parent / 'builtin_res' @@ -21,9 +22,10 @@ class TxtGameApp: self.shaders = self.SHADER_CLASS(self) self.coords = self.COORDINATE_CLASS(self) self.should_exit = False + self.handler = CallbackHandler(self) def init(self): - pass + self.platform.init_callbacks(self.window, self.handler) def start(self): self.platform.init() diff --git a/txtgameengine/input/__init__.py b/txtgameengine/input/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/txtgameengine/input/callbacks.py b/txtgameengine/input/callbacks.py new file mode 100644 index 0000000..476c103 --- /dev/null +++ b/txtgameengine/input/callbacks.py @@ -0,0 +1,31 @@ +import typing +from .keyboard import ModKey, KeyboardCallback, KeyboardEvent, KeyboardCallbackBuilder + +if typing.TYPE_CHECKING: + from ..app import TxtGameApp + + +class CallbackHandler: + def __init__(self, app: 'TxtGameApp'): + self.app = app + self.keyboard_callbacks: typing.List[KeyboardCallback] = [] + + def register_keyboard_callback(self, callback: KeyboardCallback): + self.keyboard_callbacks.append(callback) + + def get_keyboard_input_callback(self, window: typing.Any, keycode: int, scancode: int, action: int, mod_keys: int): + event = KeyboardEvent(window, keycode, scancode, action, ModKey(mod_keys)) + for callback in self.keyboard_callbacks: + if event.mod_keys == callback.required_mod_keys: + continue + + callback.callback(event) + + def get_mouse_move_callback(self, window: typing.Any, pos_x: float, pos_y: float): + pass + + def get_mouse_click_callback(self, window: typing.Any, button: int, action: int, mod_keys: int): + pass + + def keyboard_callback(self) -> KeyboardCallbackBuilder: + return KeyboardCallbackBuilder(self.app) diff --git a/txtgameengine/input/keyboard.py b/txtgameengine/input/keyboard.py new file mode 100644 index 0000000..1938016 --- /dev/null +++ b/txtgameengine/input/keyboard.py @@ -0,0 +1,52 @@ +from enum import IntFlag +import glfw +import typing +from dataclasses import dataclass + +if typing.TYPE_CHECKING: + from ..scenes import Scene + + SceneLike = typing.TypeAlias('SceneLike', typing.Union[Scene, typing.Type[Scene]]) + + +class ModKey(IntFlag): + SHIFT = glfw.MOD_SHIFT + CONTROL = glfw.MOD_CONTROL + ALT = glfw.MOD_ALT + SUPER = glfw.MOD_SUPER + + +@dataclass +class KeyboardEvent: + window: typing.Any + keycode: int + scancode: int + action: int + mod_keys: int + + def has_modkey(self, modkey: ModKey): + return bool(self.mod_keys & modkey) + + +class KeyboardCallbackBuilder: + def __init__(self, app): + self.app = app + self.scene = None + self.required_mod_keys = ModKey(0) + + def build(self, callback: typing.Callable[[KeyboardEvent], None]): + KeyboardCallback(self.required_mod_keys, callback) + + def only_in_scene(self, scene: 'SceneLike'): + self.scene = scene + return self + + def with_mod_key(self, mod_key: ModKey): + self.required_mod_keys |= mod_key + return self + + +class KeyboardCallback: + def __init__(self, required_mod_keys, callback: typing.Callable[[KeyboardEvent], None]): + self.required_mod_keys = required_mod_keys + self.callback = callback diff --git a/txtgameengine/platform.py b/txtgameengine/platform.py index cd3a17d..8258d33 100644 --- a/txtgameengine/platform.py +++ b/txtgameengine/platform.py @@ -5,6 +5,7 @@ import numpy as np from OpenGL.GL import * import OpenGL.GL.shaders as shaders from .twod import Texture +from .input.callbacks import CallbackHandler if typing.TYPE_CHECKING: from .app import TxtGameApp @@ -57,6 +58,12 @@ class PlatformComponent: def poll_events(): glfw.poll_events() + @staticmethod + def init_callbacks(window, handler: CallbackHandler): + glfw.set_key_callback(window, handler.get_keyboard_input_callback) + #glfw.set_mouse_button_callback(window, handler.get_mouse_click_callback()) + #glfw.set_cursor_pos_callback(window, handler.get_mouse_move_callback()) + def cleanup(self): glfw.destroy_window(self.app.window) glfw.terminate() diff --git a/txtgameengine/scenes.py b/txtgameengine/scenes.py index de5579c..725dbd3 100644 --- a/txtgameengine/scenes.py +++ b/txtgameengine/scenes.py @@ -1,5 +1,5 @@ import typing - +from .input.keyboard import KeyboardCallback from .app import TxtGameApp -- cgit