diff --git a/arcade/gui/__init__.py b/arcade/gui/__init__.py index 820e1f4aaf..ab125f172f 100644 --- a/arcade/gui/__init__.py +++ b/arcade/gui/__init__.py @@ -1,4 +1,4 @@ -from arcade.gui.constructs import UIMessageBox +from arcade.gui.constructs import UIMessageBox, UIButtonRow from arcade.gui.events import UIEvent from arcade.gui.events import UIKeyEvent from arcade.gui.events import UIKeyPressEvent @@ -46,6 +46,7 @@ __all__ = [ "UIAnchorLayout", "UIBoxLayout", + "UIButtonRow", "UIGridLayout", "UIManager", "UIMessageBox", diff --git a/arcade/gui/constructs.py b/arcade/gui/constructs.py index 9f706856c5..4b8ec90251 100644 --- a/arcade/gui/constructs.py +++ b/arcade/gui/constructs.py @@ -1,11 +1,12 @@ """ Constructs, are prepared widget combinations, you can use for common use-cases """ -from arcade.gui.nine_patch import NinePatchTexture +from typing import Any, Optional import arcade -from arcade.gui.events import UIOnActionEvent +from arcade.gui.events import UIOnActionEvent, UIOnClickEvent from arcade.gui.mixins import UIMouseFilterMixin +from arcade.gui.nine_patch import NinePatchTexture from arcade.gui.widgets.buttons import UIFlatButton from arcade.gui.widgets.layout import UIBoxLayout, UIAnchorLayout from arcade.gui.widgets.text import UITextArea @@ -93,3 +94,60 @@ def _on_choice(self, event): def on_action(self, event: UIOnActionEvent): """Called when button was pressed""" pass + + +class UIButtonRow(UIBoxLayout): + """ + Places buttons in a row. + :param bool vertical: Whether the button row is vertical or not. + :param str align: Where to align the button row. + :param Any size_hint: Tuple of floats (0.0 - 1.0) of how much space of the parent should be requested. + :param size_hint_min: Min width and height in pixel. + :param size_hint_max: Max width and height in pixel. + :param int space_between: The space between the children. + :param Any style: Not used. + :param Tuple[str, ...] button_labels: The labels for the buttons. + :param Callable callback: The callback function which will receive the text of the clicked button. + """ + + def __init__( + self, + vertical: bool = False, + align: str = "center", + size_hint: Any = (0, 0), + size_hint_min: Optional[Any] = None, + size_hint_max: Optional[Any] = None, + space_between: int = 10, + style: Optional[Any] = None, + button_factory: type = UIFlatButton, + ): + super().__init__( + vertical=vertical, + align=align, + size_hint=size_hint, + size_hint_min=size_hint_min, + size_hint_max=size_hint_max, + space_between=space_between, + style=style, + ) + self.register_event_type("on_action") + + self.button_factory = button_factory + + def add_button( + self, + label: str, + *, + style=None, + multiline=False, + ): + button = self.button_factory(text=label, style=style, multiline=multiline) + button.on_click = self._on_click # type: ignore + self.add(button) + return button + + def on_action(self, event: UIOnActionEvent): + pass + + def _on_click(self, event: UIOnClickEvent): + self.dispatch_event("on_action", UIOnActionEvent(self, event.source.text)) diff --git a/arcade/gui/examples/style_v2.py b/arcade/gui/examples/style_v2.py index b64d6a8735..b2b582ba75 100644 --- a/arcade/gui/examples/style_v2.py +++ b/arcade/gui/examples/style_v2.py @@ -1,11 +1,10 @@ from random import choice -from typing import Optional, Any import arcade from arcade.gui import UIManager, UIOnClickEvent -from arcade.gui.events import UIOnActionEvent +from arcade.gui.constructs import UIButtonRow from arcade.gui.widgets.buttons import UIFlatButton -from arcade.gui.widgets.layout import UIAnchorLayout, UIBoxLayout +from arcade.gui.widgets.layout import UIAnchorLayout STYLES = [ UIFlatButton.DEFAULT_STYLE, @@ -80,62 +79,6 @@ ] -class UIButtonRow(UIBoxLayout): - """ - Places buttons in a row. - :param bool vertical: Whether the button row is vertical or not. - :param str align: Where to align the button row. - :param Any size_hint: Tuple of floats (0.0 - 1.0) of how much space of the parent should be requested. - :param size_hint_min: Min width and height in pixel. - :param size_hint_max: Max width and height in pixel. - :param int space_between: The space between the children. - :param Any style: Not used. - :param Tuple[str, ...] button_labels: The labels for the buttons. - :param Callable callback: The callback function which will receive the text of the clicked button. - """ - - def __init__( - self, - vertical: bool = False, - align: str = "center", - size_hint: Any = (0, 0), - size_hint_min: Optional[Any] = None, - size_hint_max: Optional[Any] = None, - space_between: int = 10, - style: Optional[Any] = None, - button_factory: type = UIFlatButton, - ): - super().__init__( - vertical=vertical, - align=align, - size_hint=size_hint, - size_hint_min=size_hint_min, - size_hint_max=size_hint_max, - space_between=space_between, - style=style, - ) - self.register_event_type("on_action") - - self.button_factory = button_factory - - def add_button( - self, - label: str, - *, - style=None, - ): - button = self.button_factory(text=label, style=style, multiline=True) - button.on_click = self._on_click # type: ignore - self.add(button) - return button - - def on_action(self, event: UIOnActionEvent): - pass - - def _on_click(self, event: UIOnClickEvent): - self.dispatch_event("on_action", UIOnActionEvent(self, event.source.text)) - - class DemoWindow(arcade.Window): def __init__(self): super().__init__(800, 600, "UI Mockup", resizable=True) @@ -151,7 +94,7 @@ def __init__(self): anchor = self.manager.add(UIAnchorLayout()) row = anchor.add(UIButtonRow(button_factory=UIFlatButton)) - button1 = row.add_button("Click me to switch style") + button1 = row.add_button("Click me to switch style", multiline=True) @button1.event("on_click") def change_style(event: UIOnClickEvent): @@ -159,7 +102,7 @@ def change_style(event: UIOnClickEvent): btn.style = choice([s for s in STYLES if s is not btn.style]) btn.trigger_render() - button2 = row.add_button("Toggle disable") + button2 = row.add_button("Toggle disable", multiline=True) @button2.event("on_click") def toggle(*_): diff --git a/doc/programming_guide/release_notes.rst b/doc/programming_guide/release_notes.rst index fa5bbba690..d1803725f2 100644 --- a/doc/programming_guide/release_notes.rst +++ b/doc/programming_guide/release_notes.rst @@ -110,6 +110,7 @@ Changes * :py:class:`~arcade.gui.widgets.dropdown.UIDropdown` * :py:class:`~arcade.gui.widgets.slider.UISlider` + * :py:class:`~arcade.gui.widgets.constructs.UIButtonRow` (`PR1580 `_ and `PR1253 `_) * Arcade :py:class:`~arcade.gui.property.Property`: