scenex.app.events#
scenex.app.events
#
Event system for handling user input and interaction.
This module provides a unified event abstraction for user interactions across different GUI frameworks and rendering backends. Events represent user actions (e.g. mouse clicks, movement, scrolling) and system events (e.g. window resize), allowing event filters, camera controllers, etc. to respond to input in a framework-agnostic way.
Event Types
Keyboard Events: - KeyPressEvent: Key pressed - KeyReleaseEvent: Key released
Mouse Events: - MousePressEvent: Mouse button pressed - MouseReleaseEvent: Mouse button released - MouseMoveEvent: Mouse cursor moved - MouseDoublePressEvent: Mouse button double-pressed - MouseEnterEvent: Mouse entered a view - MouseLeaveEvent: Mouse left a view - WheelEvent: Mouse wheel scrolled
System Events: - ResizeEvent: Canvas window resized
Event Flow
Events are dispatched by the canvas to views and their camera controllers::
Canvas → View (filter_event) → Camera Controller (handle_event)
The flow works as follows: 1. Canvas determines which view contains the cursor position 2. Canvas calls the view's filter_event() method with the event 3. If the view's camera is interactive, the camera controller's handle_event() is called 4. Handlers return True to stop propagation or False to continue
Key Concepts
Ray: 3D ray in world space representing the mouse position - Used for 3D picking and intersection tests - Computed from 2D canvas position via camera unprojection
MouseButton: Enumeration of mouse buttons (LEFT, RIGHT, MIDDLE, etc.)
Examples:
Set a custom event filter on a view::
from scenex.model import View
from scenex.app.events import MousePressEvent
def on_click(event):
if isinstance(event, MousePressEvent):
print(f"Clicked at {event.canvas_pos}")
return True # Event handled
return False
view = View(scene=my_scene, camera=my_camera)
view.set_event_filter(on_click)
See Also
scenex.model.Camera : Camera with interactive interaction strategies scenex.model.View : View with event filter support
Classes:
-
Event–Base class for all user interaction and system events.
-
EventFilter–Base class for event filter handles.
-
KeyEvent–Base class for keyboard events.
-
KeyPressEvent–Keyboard key press.
-
KeyReleaseEvent–Keyboard key release.
-
MouseButton–Enumeration of mouse button states as bit flags.
-
MouseDoublePressEvent–Mouse button double-click.
-
MouseEnterEvent–Mouse cursor entering the view area.
-
MouseEvent–Base class for all mouse-related interaction events.
-
MouseLeaveEvent–Mouse cursor leaving the view area.
-
MouseMoveEvent–Mouse cursor movement within the view.
-
MousePressEvent–Mouse button press.
-
MouseReleaseEvent–Mouse button release.
-
Ray–A 3D ray in world space representing a mouse position.
-
ResizeEvent–Window resize event.
-
WheelEvent–Mouse wheel scroll event.
Event
dataclass
#
Event()
Base class for all user interaction and system events.
Event is the root of the event hierarchy in scenex. All specific event types (mouse, keyboard, resize) inherit from this base class, enabling polymorphic event handling and extensibility for custom event types.
The inheritance-based design allows: - Type checking with isinstance() to discriminate event types - Extensibility for adding new event types downstream - Structured event filtering based on event class hierarchy
See Also
MouseEvent : Base class for mouse-related events ResizeEvent : Window resize event
EventFilter
#
Bases: ABC
flowchart TD
scenex.app.events.EventFilter[EventFilter]
click scenex.app.events.EventFilter href "" "scenex.app.events.EventFilter"
Base class for event filter handles.
EventFilter instances are returned when installing event filters on views or canvases. They provide a mechanism to uninstall the filter when it's no longer needed, ensuring proper cleanup and preventing memory leaks.
Methods:
-
uninstall–Remove this event filter.
uninstall
abstractmethod
#
uninstall() -> None
Remove this event filter.
Uninstalls the event filter, ensuring that the filter function will no longer be called for future events. After calling uninstall(), this EventFilter instance should not be used further.
Source code in src/scenex/app/events/_events.py
402 403 404 405 406 407 408 409 410 | |
KeyEvent
dataclass
#
KeyEvent(key: KeyBinding)
Bases: Event
flowchart TD
scenex.app.events.KeyEvent[KeyEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.Event --> scenex.app.events.KeyEvent
click scenex.app.events.KeyEvent href "" "scenex.app.events.KeyEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Base class for keyboard events.
Attributes:
-
key(KeyBinding) –The key (or chord) that was pressed or released. Use
KeyBinding.from_str("Ctrl+A")to construct from a string, or accesskey.part0for the first (usually only) key and its modifier state (ctrl,shift,alt,meta).
See Also
KeyPressEvent : Key press KeyReleaseEvent : Key release
KeyPressEvent
dataclass
#
KeyPressEvent(key: KeyBinding)
Bases: KeyEvent
flowchart TD
scenex.app.events.KeyPressEvent[KeyPressEvent]
scenex.app.events._events.KeyEvent[KeyEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.KeyEvent --> scenex.app.events.KeyPressEvent
scenex.app.events._events.Event --> scenex.app.events._events.KeyEvent
click scenex.app.events.KeyPressEvent href "" "scenex.app.events.KeyPressEvent"
click scenex.app.events._events.KeyEvent href "" "scenex.app.events._events.KeyEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Keyboard key press.
See Also
KeyReleaseEvent : Key release
KeyReleaseEvent
dataclass
#
KeyReleaseEvent(key: KeyBinding)
Bases: KeyEvent
flowchart TD
scenex.app.events.KeyReleaseEvent[KeyReleaseEvent]
scenex.app.events._events.KeyEvent[KeyEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.KeyEvent --> scenex.app.events.KeyReleaseEvent
scenex.app.events._events.Event --> scenex.app.events._events.KeyEvent
click scenex.app.events.KeyReleaseEvent href "" "scenex.app.events.KeyReleaseEvent"
click scenex.app.events._events.KeyEvent href "" "scenex.app.events._events.KeyEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Keyboard key release.
See Also
KeyPressEvent : Key press
MouseButton
#
Bases: IntFlag
flowchart TD
scenex.app.events.MouseButton[MouseButton]
click scenex.app.events.MouseButton href "" "scenex.app.events.MouseButton"
Enumeration of mouse button states as bit flags.
MouseButton uses IntFlag to allow bitwise operations, enabling representation of multiple simultaneous button presses.
Examples:
Check if left button is pressed:
>>> event = MousePressEvent(
... pos=(100, 150),
... buttons=MouseButton.LEFT | MouseButton.RIGHT,
... )
>>> if event.buttons & MouseButton.LEFT:
... print("Left button is down")
Left button is down
Check for specific button combination:
>>> if event.buttons == (MouseButton.LEFT | MouseButton.RIGHT):
... print("Both left and right buttons pressed")
Both left and right buttons pressed
Check if any button is pressed:
>>> if event.buttons != MouseButton.NONE:
... print("Some button is pressed")
Some button is pressed
MouseDoublePressEvent
dataclass
#
MouseDoublePressEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: MouseEvent
flowchart TD
scenex.app.events.MouseDoublePressEvent[MouseDoublePressEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.MouseDoublePressEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.MouseDoublePressEvent href "" "scenex.app.events.MouseDoublePressEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse button double-click.
Fired when a mouse button is double-clicked (pressed twice in rapid succession). The timing threshold for double-click detection is system-dependent.
See Also
MousePressEvent : Single mouse button press
MouseEnterEvent
dataclass
#
MouseEnterEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: MouseEvent
flowchart TD
scenex.app.events.MouseEnterEvent[MouseEnterEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.MouseEnterEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.MouseEnterEvent href "" "scenex.app.events.MouseEnterEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse cursor entering the view area.
Fired when the mouse cursor enters the bounds of a view from outside. Includes the entry position and button states.
See Also
MouseLeaveEvent : Mouse cursor leaving the view
MouseEvent
dataclass
#
MouseEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: Event
flowchart TD
scenex.app.events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.Event --> scenex.app.events.MouseEvent
click scenex.app.events.MouseEvent href "" "scenex.app.events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Base class for all mouse-related interaction events.
MouseEvent provides common fields for all mouse interactions, including the 2D position and the state of mouse buttons. Specific mouse event types (move, press, release, etc.) inherit from this base.
To obtain the 3D world ray for a mouse event, use View.to_ray().
Attributes:
-
pos(tuple[float, float]) –The (x, y) position of the mouse cursor in pixel coordinates, with origin at the top-left corner.
-
buttons(MouseButton) –Bit flags indicating which mouse buttons are currently pressed. Use bitwise operations to test button states (e.g., buttons & MouseButton.LEFT).
See Also
MouseMoveEvent : Mouse cursor movement MousePressEvent : Mouse button press MouseReleaseEvent : Mouse button release WheelEvent : Mouse wheel scroll
MouseLeaveEvent
dataclass
#
MouseLeaveEvent()
Bases: Event
flowchart TD
scenex.app.events.MouseLeaveEvent[MouseLeaveEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.Event --> scenex.app.events.MouseLeaveEvent
click scenex.app.events.MouseLeaveEvent href "" "scenex.app.events.MouseLeaveEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse cursor leaving the view area.
Fired when the mouse cursor exits the bounds of a view. This is distinct from other mouse events in that it does not include position or button information, as the cursor is no longer over the view.
Note that this does not inherit from MouseEvent, as no position or buttons are available when the cursor has left the view.
See Also
MouseEnterEvent : Mouse cursor entering the view
MouseMoveEvent
dataclass
#
MouseMoveEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: MouseEvent
flowchart TD
scenex.app.events.MouseMoveEvent[MouseMoveEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.MouseMoveEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.MouseMoveEvent href "" "scenex.app.events.MouseMoveEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse cursor movement within the view.
Fired when the mouse cursor moves within the view bounds. Includes the current position, world ray, and button states. This event fires continuously during cursor movement.
MousePressEvent
dataclass
#
MousePressEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: MouseEvent
flowchart TD
scenex.app.events.MousePressEvent[MousePressEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.MousePressEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.MousePressEvent href "" "scenex.app.events.MousePressEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse button press.
Fired when a mouse button is pressed down. The buttons field indicates which button(s) are now pressed. For detecting which button was newly pressed, compare with previous button states.
See Also
MouseReleaseEvent : Mouse button release MouseDoublePressEvent : Double-click detection
MouseReleaseEvent
dataclass
#
MouseReleaseEvent(pos: tuple[float, float], buttons: MouseButton)
Bases: MouseEvent
flowchart TD
scenex.app.events.MouseReleaseEvent[MouseReleaseEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.MouseReleaseEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.MouseReleaseEvent href "" "scenex.app.events.MouseReleaseEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse button release.
Fired when a mouse button is released. The buttons field reflects the state after the release (i.e., the released button is no longer set in the flags).
See Also
MousePressEvent : Mouse button press
Ray
#
Bases: NamedTuple
flowchart TD
scenex.app.events.Ray[Ray]
click scenex.app.events.Ray href "" "scenex.app.events.Ray"
A 3D ray in world space representing a mouse position.
A Ray represents the path of the mouse cursor projected into 3D world space, starting from the camera and passing through the cursor position on the view. Rays are the fundamental mechanism for 3D picking and intersection testing, allowing determination of which scene objects are under the mouse cursor.
The ray is defined by an origin point (typically the camera position) and a normalized direction vector, and can be used to test intersections with scene geometry.
Attributes:
-
origin(tuple[float, float, float]) –The starting point of the ray in world coordinates, typically the camera position for perspective projections or a point on the view plane for orthographic projections.
-
direction(tuple[float, float, float]) –The normalized direction vector of the ray in world coordinates. For perspective views, this points from the camera through the cursor. For orthographic views, this is parallel to the camera's view direction.
-
source(View) –The view that generated this ray, providing context for which camera and scene the ray originated from.
Examples:
Find all intersections with a scene:
>>> import numpy as np
>>> import scenex as snx
>>> view = snx.View(
... scene=snx.Scene(
... children=[
... snx.Image(data=np.random.rand(100, 100)),
... snx.Points(
... vertices=np.asarray([[0, 0, 0], [1, 1, 0]]),
... size=5,
... edge_width=0,
... ),
... ]
... )
... )
>>> ray = Ray(origin=(1, 1, 10), direction=(0, 0, -1), source=view)
>>> ray.intersections(view.scene)
[(Points(...), 7.5), (Image(...), 10.0)]
See Also
View.to_ray : Method to compute a Ray from a canvas position Node.passes_through : Node method for computing ray intersections
Methods:
-
intersections–Find all nodes intersected by this ray in the scene graph.
-
point_at_distance–Compute the 3D point at a given distance along the ray.
intersections
#
Find all nodes intersected by this ray in the scene graph.
Recursively tests the ray against the given node and all its descendants, returning all intersections sorted by distance from the ray origin. Only visible nodes are tested.
Parameters:
Returns:
-
list[Intersection]–List of (node, distance) tuples for all intersections, sorted by increasing distance from the ray origin. The distance is the parameter t where intersection occurs at origin + t * direction.
Source code in src/scenex/app/events/_events.py
155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 | |
point_at_distance
#
Compute the 3D point at a given distance along the ray.
Parameters:
-
(distance#float) –The distance along the ray from the origin. Positive values extend in the direction of the ray, negative values extend backward from the origin.
Returns:
-
tuple[float, float, float]–The (x, y, z) coordinates of the point at the specified distance along the ray.
Source code in src/scenex/app/events/_events.py
134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 | |
ResizeEvent
dataclass
#
Bases: Event
flowchart TD
scenex.app.events.ResizeEvent[ResizeEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.Event --> scenex.app.events.ResizeEvent
click scenex.app.events.ResizeEvent href "" "scenex.app.events.ResizeEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Window resize event.
Fired when a window changes dimensions, whether from user interaction (dragging window edges), programmatic resizing, or window manager actions. This event allows views and other components to adapt to new window dimensions.
Attributes:
-
width(int) –The new width of the window in pixels.
-
height(int) –The new height of the window in pixels.
WheelEvent
dataclass
#
Bases: MouseEvent
flowchart TD
scenex.app.events.WheelEvent[WheelEvent]
scenex.app.events._events.MouseEvent[MouseEvent]
scenex.app.events._events.Event[Event]
scenex.app.events._events.MouseEvent --> scenex.app.events.WheelEvent
scenex.app.events._events.Event --> scenex.app.events._events.MouseEvent
click scenex.app.events.WheelEvent href "" "scenex.app.events.WheelEvent"
click scenex.app.events._events.MouseEvent href "" "scenex.app.events._events.MouseEvent"
click scenex.app.events._events.Event href "" "scenex.app.events._events.Event"
Mouse wheel scroll event.
Fired when the mouse wheel (or trackpad scroll) is used. Includes the scroll delta in both horizontal and vertical directions. The magnitude and units of angle_delta are platform-dependent but typically represent degrees or steps.
Attributes:
-
angle_delta(tuple[float, float]) –The (horizontal, vertical) scroll delta. Positive vertical values typically represent scrolling up/away from the user, negative values down/toward the user. Horizontal scrolling (if supported) uses the first component.