Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding SpinBoxUI to the UI module #499

Merged
merged 62 commits into from
Aug 10, 2023
Merged
Show file tree
Hide file tree
Changes from 11 commits
Commits
Show all changes
62 commits
Select commit Hold shift + click to select a range
ebcdef1
adding spinui
ganimtron-10 Sep 5, 2021
ef29559
repositing elements in panel
ganimtron-10 Sep 9, 2021
e31d66f
adding button callbacks, and some value parameters
ganimtron-10 Sep 12, 2021
584a23a
adding resize method
ganimtron-10 Sep 13, 2021
3644d4a
Merge branch 'fury-gl:master' into spinboxui
ganimtron-10 Sep 13, 2021
4c122ab
adding tests and hook
ganimtron-10 Sep 14, 2021
6a62630
Merge branch 'spinboxui' of https://github.com/ganimtron-10/fury into…
ganimtron-10 Sep 14, 2021
6ba4283
updating tests
ganimtron-10 Sep 14, 2021
fc62100
pep fixs
ganimtron-10 Sep 14, 2021
e1cb2f2
pep fixs
ganimtron-10 Sep 14, 2021
fc74020
updating in/decrement callback functions
ganimtron-10 Sep 14, 2021
1f2b6db
updating tutorial
ganimtron-10 Sep 16, 2021
9bc7ec9
updating docstring and alignment issue
ganimtron-10 Sep 18, 2021
3deee9f
pep fixs
ganimtron-10 Sep 18, 2021
4f04f18
adding on_blur hook in TextBox2D
ganimtron-10 Sep 18, 2021
30b2cad
changing value using textbox
ganimtron-10 Sep 18, 2021
e5b8de5
updating tests
ganimtron-10 Sep 18, 2021
c9eeefd
pep fix
ganimtron-10 Sep 18, 2021
600383d
Merge branch 'textbox_hook' into spinboxui
ganimtron-10 Oct 15, 2021
ee3377a
updating the textboxhook name
ganimtron-10 Oct 15, 2021
8d3dd85
changes from fury master
ganimtron-10 Jan 20, 2022
373529f
updating test file
ganimtron-10 Jan 20, 2022
42430da
merging master
ganimtron-10 Apr 22, 2022
d7af56d
Merge branch 'fury-gl-master' into spinboxui
ganimtron-10 Apr 22, 2022
2915ca2
updating test file
ganimtron-10 Apr 23, 2022
e585ce6
Merge branch 'master' into spinboxui
ganimtron-10 Jul 23, 2022
da87c65
Merge branch 'master' into spinboxui
ganimtron-10 Aug 19, 2022
7036d70
updating pep formatting
ganimtron-10 Aug 19, 2022
e246386
Merge branch 'master' into spinboxui
ganimtron-10 Nov 12, 2022
2c268da
Merge branch 'fury-gl:master' into spinboxui
ganimtron-10 Nov 18, 2022
b9f7489
adding spinui
ganimtron-10 Sep 5, 2021
4b69145
repositing elements in panel
ganimtron-10 Sep 9, 2021
a6fadf7
adding button callbacks, and some value parameters
ganimtron-10 Sep 12, 2021
bd27434
adding resize method
ganimtron-10 Sep 13, 2021
f6e9296
adding tests and hook
ganimtron-10 Sep 14, 2021
ba7089b
updating tests
ganimtron-10 Sep 14, 2021
34ed09d
pep fixs
ganimtron-10 Sep 14, 2021
ffb0c93
updating in/decrement callback functions
ganimtron-10 Sep 14, 2021
b9a0432
updating tutorial
ganimtron-10 Sep 16, 2021
46b8eb2
updating docstring and alignment issue
ganimtron-10 Sep 18, 2021
7755035
pep fixs
ganimtron-10 Sep 18, 2021
0d36286
changing value using textbox
ganimtron-10 Sep 18, 2021
f969c8e
updating tests
ganimtron-10 Sep 18, 2021
739640c
pep fix
ganimtron-10 Sep 18, 2021
dbc9932
updating the textboxhook name
ganimtron-10 Oct 15, 2021
3dc951a
updating test file
ganimtron-10 Jan 20, 2022
1b05168
updating test file
ganimtron-10 Apr 23, 2022
e8de3b4
updating pep formatting
ganimtron-10 Aug 19, 2022
5363291
updating test file
ganimtron-10 Apr 21, 2023
d597fe8
Merge branch 'master' into spinboxui
ganimtron-10 Jun 2, 2023
a30d6f2
aligning the text to the center
ganimtron-10 Jun 4, 2023
061b594
Merge branch 'master' into spinboxui
ganimtron-10 Jul 30, 2023
d891f83
Merge branch 'master' into spinboxui
ganimtron-10 Jul 30, 2023
22ff592
Merge branch 'master' into spinboxui
ganimtron-10 Aug 7, 2023
4130d1e
updating the textbox to automatically scale
ganimtron-10 Aug 7, 2023
9d286a2
skipping new line in the textbox
ganimtron-10 Aug 7, 2023
81be226
updating parameter names
ganimtron-10 Aug 8, 2023
5f7fb62
renaming paramters
ganimtron-10 Aug 9, 2023
ad08db8
adding validation for textbox input
ganimtron-10 Aug 9, 2023
ebf1a25
updating test
ganimtron-10 Aug 9, 2023
315a7ba
adding examples to valid examples file
ganimtron-10 Aug 10, 2023
b3fe482
fix typo before merging
skoudoro Aug 10, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
63 changes: 63 additions & 0 deletions docs/tutorials/02_ui/viz_spinbox.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
# -*- coding: utf-8 -*-
"""
===========
SpinBox UI
===========

This example shows how to use the UI API. We will demonstrate how to create
a SpinBox UI.

First, some imports.
"""
from fury import actor, ui, window
import numpy as np
from fury.data import read_viz_icons, fetch_viz_icons
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved

##############################################################################
# First we need to fetch some icons that are included in FURY.

fetch_viz_icons()

###############################################################################
# Let's create a Cone.

cone = actor.cone(np.random.rand(1, 3), np.random.rand(1, 3), (1, 1, 1),
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
np.random.rand(1))

###############################################################################
# Creating the SpinBox UI.

spinbox = ui.SpinBox(position=(200, 100), size=(300, 100), min_val=0,
max_val=360, initial_val=180, step=10)

###############################################################################
# Now that all the elements have been initialised, we add them to the show
# manager.

current_size = (800, 800)
show_manager = window.ShowManager(size=current_size,
title="FURY SpinBox Example")

show_manager.scene.add(cone)
show_manager.scene.add(spinbox)

###############################################################################
# Using the on_change hook to rotate the scene.


def rotate_cone(spinbox):
show_manager.scene.azimuth(spinbox.value)
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved


spinbox.on_change = rotate_cone

###############################################################################
# Starting the ShowManager.

interactive = False

if interactive:
show_manager.start()

window.record(show_manager.scene, size=current_size,
out_path="viz_spinbox.png")
1 change: 1 addition & 0 deletions fury/data/files/test_ui_spinbox.json
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"CharEvent": 4, "MouseMoveEvent": 347, "KeyPressEvent": 4, "KeyReleaseEvent": 4, "LeftButtonPressEvent": 43, "LeftButtonReleaseEvent": 43, "RightButtonPressEvent": 0, "RightButtonReleaseEvent": 0, "MiddleButtonPressEvent": 0, "MiddleButtonReleaseEvent": 0}
Binary file added fury/data/files/test_ui_spinbox.log.gz
Binary file not shown.
163 changes: 162 additions & 1 deletion fury/ui/elements.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@

__all__ = ["TextBox2D", "LineSlider2D", "LineDoubleSlider2D",
"RingSlider2D", "RangeSlider", "Checkbox", "Option", "RadioButton",
"ComboBox2D", "ListBox2D", "ListBoxItem2D", "FileMenu2D"]
"ComboBox2D", "ListBox2D", "ListBoxItem2D", "FileMenu2D",
"SpinBox"]

import os
from collections import OrderedDict
Expand Down Expand Up @@ -3052,3 +3053,163 @@ def directory_click_callback(self, i_ren, _obj, listboxitem):
self.set_slot_colors()
i_ren.force_render()
i_ren.event.abort()


class SpinBox(UI):
"""SpinBox UI.
"""

def __init__(self, position=(350, 400), size=(300, 100), padding=10,
panel_color=(1, 1, 1), min_val=0, max_val=100,
initial_val=50, step=1):
"""Init this UI element.

Parameters
----------
position : (float, float), optional
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
Absolute coordinates (x, y) of the lower-left corner of this
UI component.
size : (float, float), optional
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
Width and height in pixels of this UI component.
padding : float, optional
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
Distance between and background.
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
bg_color : (float, float, float), optional
Background color of progress bar.
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
min_val: float, optional
Minimum value of SpinBoxUI.
max_val: float, optional
Maximum value of SpinBoxUI.
initial_val: float, optional
Initial value of SpinBoxUI.
step: float, optional
Step value of SpinBoxUI.
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
"""
self.panel_size = size
self.padding = padding
self.panel_color = panel_color
self.min_val = min_val
self.max_val = max_val
self.value = initial_val
self.step = step

super(SpinBox, self).__init__(position)

self.resize(size)

self.on_change = lambda ui: None

def _setup(self):
"""Setup this UI component.

Create the SpinBoxUI with Background (Panel2D) and InputBox (TextBox2D)
and Increment,Decrement Button (Button2D).
"""
self.panel = Panel2D(size=self.panel_size, color=self.panel_color)

self.textbox = TextBox2D(width=10, height=2)
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
self.textbox.set_message(str(self.value))
self.increment_button = Button2D(
icon_fnames=[("up", read_viz_icons(fname="circle-up.png"))])
self.decrement_button = Button2D(
icon_fnames=[("down", read_viz_icons(fname="circle-down.png"))])

self.panel.add_element(self.textbox, (0, 0))
self.panel.add_element(self.increment_button, (0, 0))
self.panel.add_element(self.decrement_button, (0, 0))

# Adding button click callbacks
self.increment_button.on_left_mouse_button_pressed = \
self.increment_callback
self.decrement_button.on_left_mouse_button_pressed = \
self.decrement_callback

def resize(self, size):
"""Resize SpinBox.

Parameters
----------
size : (float, float)
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
SpinBox size(width, height) in pixels.
"""
self.panel_size = size
self.textbox_size = (int(0.7 * size[0]), int(0.8 * size[1]))
self.button_size = (int(0.2 * size[0]), int(0.3 * size[1]))

self.panel.resize(size)
self.textbox.text.resize(self.textbox_size)
self.increment_button.resize(self.button_size)
self.decrement_button.resize(self.button_size)

textbox_pos = (self.padding, int((size[1] - self.textbox_size[1])/2))
inc_btn_pos = (size[0] - self.padding - self.button_size[0],
int((1.5*size[1] - self.button_size[1])/2))
dec_btn_pos = (size[0] - self.padding - self.button_size[0],
int((0.5*size[1] - self.button_size[1])/2))

self.panel.update_element(self.textbox, textbox_pos)
self.panel.update_element(self.increment_button, inc_btn_pos)
self.panel.update_element(self.decrement_button, dec_btn_pos)

def _get_actors(self):
"""Get the actors composing this UI component."""
return self.panel.actors

def _add_to_scene(self, scene):
"""Add all subcomponents or VTK props that compose this UI component.

Parameters
----------
scene : Scene

"""
self.panel.add_to_scene(scene)

def _get_size(self):
return self.panel.size

def _set_position(self, coords):
"""Set the lower-left corner position of this UI component.

Parameters
----------
coords: (float, float)
Absolute pixel coordinates (x, y).
"""
self.panel.center = coords

def increment_callback(self, i_ren, _obj, _button):
self.increment()
i_ren.force_render()
i_ren.event.abort()

def decrement_callback(self, i_ren, _obj, _button):
self.decrement()
i_ren.force_render()
i_ren.event.abort()

@property
def value(self):
return self._value

@value.setter
def value(self, value):
if value > self.max_val:
self._value = self.max_val
elif value < self.min_val:
self._value = self.min_val
else:
self._value = value

def increment(self):
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
current_val = int(self.textbox.message)
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
self.value = current_val + self.step

self.textbox.set_message(str(self.value))
self.on_change(self)

def decrement(self):
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
current_val = int(self.textbox.message)
ganimtron-10 marked this conversation as resolved.
Show resolved Hide resolved
self.value = current_val - self.step

self.textbox.set_message(str(self.value))
self.on_change(self)
30 changes: 30 additions & 0 deletions fury/ui/tests/test_elements.py
Original file line number Diff line number Diff line change
Expand Up @@ -789,6 +789,36 @@ def test_ui_combobox_2d(interactive=False):
npt.assert_equal((450, 210), combobox.drop_menu_size)


def test_ui_spinbox(interactive=False):
filename = "test_ui_spinbox"
recording_filename = pjoin(DATA_DIR, filename + ".log.gz")
expected_events_counts_filename = pjoin(DATA_DIR, filename + ".json")

spinbox = ui.SpinBox(size=(300, 200), min_val=-20, max_val=10, step=2)

# Assign the counter callback to every possible event.
event_counter = EventCounter()
event_counter.monitor(spinbox)

current_size = (800, 800)
show_manager = window.ShowManager(
size=current_size, title="SpinBox UI Example")
show_manager.scene.add(spinbox)

if interactive:
show_manager.record_events_to_file(recording_filename)
print(list(event_counter.events_counts.items()))
event_counter.save(expected_events_counts_filename)

else:
show_manager.play_events_from_file(recording_filename)
expected = EventCounter.load(expected_events_counts_filename)
event_counter.check_counts(expected)

spinbox.resize((450, 200))
npt.assert_equal((315, 160), spinbox.textbox_size)
npt.assert_equal((90, 60), spinbox.button_size)

def test_frame_rate_and_anti_aliasing():
"""Testing frame rate with/out anti-aliasing"""

Expand Down