Skip to content

Commit e353a52

Browse files
authored
Merge pull request #449 from ppizarror/theme-add-alignment-ignore-scrollbar
Added theme.widget_alignment_ignore_scrollbar_thickness
2 parents 721d45a + 98e5af3 commit e353a52

File tree

3 files changed

+33
-3
lines changed

3 files changed

+33
-3
lines changed

pygame_menu/menu.py

+7-3
Original file line numberDiff line numberDiff line change
@@ -1556,9 +1556,6 @@ def get_rect(wid: 'Widget') -> 'pygame.Rect':
15561556
y=menubar_height + padding[0] + d_border)
15571557
continue
15581558

1559-
# Update the position of the widget
1560-
widget.set_position(x_coord, y_coord)
1561-
15621559
# Add the widget translation to the widget for computing the min/max position. This
15631560
# feature does not work as intended as there's edge cases not covered, and centering makes
15641561
# the translation more difficult
@@ -1572,6 +1569,13 @@ def get_rect(wid: 'Widget') -> 'pygame.Rect':
15721569
min_x = min(min_x, x_coord - padding[3] - sm_left)
15731570
min_y = min(min_y, y_coord - padding[0])
15741571

1572+
# Restore the discounted scrollbar thickness
1573+
if self._theme.widget_alignment_ignore_scrollbar_thickness:
1574+
x_coord += self._get_scrollbar_thickness()[1] / 2
1575+
1576+
# Update the position of the widget
1577+
widget.set_position(x_coord, y_coord)
1578+
15751579
# Update position
15761580
if min_max_updated:
15771581
self._widget_max_position = (max_x, max_y)

pygame_menu/themes.py

+4
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,8 @@ class Theme(object):
167167
:type title_updates_pygame_display: bool
168168
:param widget_alignment: Widget default `alignment <https://pygame-menu.readthedocs.io/en/latest/_source/themes.html#alignment>`_. See :py:mod:`pygame_menu.locals`
169169
:type widget_alignment: str
170+
:param widget_alignment_ignore_scrollbar_thickness: Widget positioning ignores the scrollbar thickness. If ``True``, the widgets only consider the menu size, ignoring the thickness of the visible scrollbars
171+
:type widget_alignment_ignore_scrollbar_thickness: bool
170172
:param widget_background_color: Background color of a widget, it can be a color, ``None`` (transparent), or a BaseImage object. Background fills the entire widget + the padding
171173
:type widget_background_color: tuple, list, str, int, :py:class:`pygame.Color`, :py:class:`pygame_menu.baseimage.BaseImage`, None
172174
:param widget_background_inflate: Inflate background on x-axis and y-axis (x, y) in px. By default, it uses the highlight margin. This parameter is visual only. For modifying widget size use padding instead
@@ -284,6 +286,7 @@ class Theme(object):
284286
title_offset: Tuple2NumberType
285287
title_updates_pygame_display: bool
286288
widget_alignment: str
289+
widget_alignment_ignore_scrollbar_thickness: bool
287290
widget_background_color: Optional[Union[ColorType, 'BaseImage']]
288291
widget_background_inflate: Tuple2IntType
289292
widget_background_inflate_to_selection: bool
@@ -378,6 +381,7 @@ def __init__(self, **kwargs) -> None:
378381

379382
# Generic widget themes
380383
self.widget_alignment = self._get(kwargs, 'widget_alignment', 'alignment', ALIGN_CENTER)
384+
self.widget_alignment_ignore_scrollbar_thickness = self._get(kwargs, 'widget_alignment_ignore_scrollbar_thickness', bool, False)
381385
self.widget_background_color = self._get(kwargs, 'widget_background_color', 'color_image_none')
382386
self.widget_background_inflate = self._get(kwargs, 'background_inflate', 'tuple2int', (0, 0))
383387
self.widget_background_inflate_to_selection = self._get(kwargs, 'widget_background_inflate_to_selection', bool,

test/test_widgets.py

+22
Original file line numberDiff line numberDiff line change
@@ -542,3 +542,25 @@ def test_widget_floating_zero(self) -> None:
542542
image_widget.translate(-50, 0)
543543
menu.render()
544544
self.assertEqual(image_widget.get_position(), (-42, 60))
545+
546+
def test_widget_center_overflow_ignore_scrollbar_thickness(self) -> None:
547+
"""
548+
Test widget centering if overflow ignores scrollbar thickness.
549+
"""
550+
theme = TEST_THEME.copy()
551+
552+
menu = MenuUtils.generic_menu(width=320, theme=theme)
553+
for i in range(5):
554+
menu.add.button(f'Option{i + 1}')
555+
menu.add.button('Quit', pygame_menu.events.EXIT)
556+
557+
pos_before = menu.get_selected_widget().get_position()
558+
theme.widget_alignment_ignore_scrollbar_thickness = True
559+
menu.render()
560+
pos_after = menu.get_selected_widget().get_position()
561+
562+
# If we ignore scrollbar thickess in position, the difference
563+
# should be equal to the half of the scrollbar thickness (because
564+
# we have centered alignment)
565+
self.assertEqual(pos_after[0] - pos_before[0], menu._get_scrollbar_thickness()[1] / 2) # x
566+
self.assertEqual(pos_after[1], pos_before[1]) # y

0 commit comments

Comments
 (0)