To create a menu system, you can implement a protocol-based approach using MenuItem and ListMenu.
MenuItem Protocol: Defines the interface for menu items. Any class implementing this must provide on_event(event) to handle interactions and on_draw(console, x, y, highlight) to render the item.SelectItem: A concrete implementation of MenuItem that represents a clickable/selectable label. It triggers a callback when the user presses RETURN, RETURN2, KP_ENTER, or performs a MouseButtonUp with the LEFT button.ListMenu: A State subclass that manages a collection of MenuItem objects. It handles navigation via DIRECTION_KEYS, mouse motion for selection, and provides an on_cancel method (typically returning Pop()) triggered by ESCAPE or a right-click.
from typing import Protocol
import tcod.console
import tcod.event
from game.state import State, StateResult
class MenuItem(Protocol):
def on_event(self, event: tcod.event.Event) -> StateResult:
...
def on_draw(self, console: tcod.console.Console, x: int, y: int, highlight: bool) -> None:
...
class SelectItem: # Implementation of MenuItem
def on_event(self, event: tcod.event.Event) -> StateResult:
# Handles RETURN or MouseButton.LEFT
...
def on_draw(self, console: tcod.console.Console, x: int, y: int, highlight: bool) -> None:
# Renders the label
...