From c73415b4ba1feac9ba68cd43d12d6ff9d89d858c Mon Sep 17 00:00:00 2001 From: Fireclaw Date: Sun, 23 Feb 2020 15:23:39 +0100 Subject: [PATCH] dgui: fix sizing after changing Slider/Scrollbar orientation Closes #700 --- direct/src/gui/DirectScrollBar.py | 27 +++++++++++++++++++++++++++ direct/src/gui/DirectSlider.py | 28 +++++++++++++++++++++++++++- tests/gui/test_DirectSlider.py | 29 +++++++++++++++++++++++++++++ 3 files changed, 83 insertions(+), 1 deletion(-) create mode 100644 tests/gui/test_DirectSlider.py diff --git a/direct/src/gui/DirectScrollBar.py b/direct/src/gui/DirectScrollBar.py index a873924456..822cb5b3a6 100644 --- a/direct/src/gui/DirectScrollBar.py +++ b/direct/src/gui/DirectScrollBar.py @@ -88,6 +88,8 @@ class DirectScrollBar(DirectFrame): else: self.incButton['frameSize'] = (f[0], f[1], f[2]*0.05, f[3]*0.05) + self._lastOrientation = self['orientation'] + self.guiItem.setThumbButton(self.thumb.guiItem) self.guiItem.setLeftButton(self.decButton.guiItem) self.guiItem.setRightButton(self.incButton.guiItem) @@ -140,13 +142,38 @@ class DirectScrollBar(DirectFrame): def setOrientation(self): if self['orientation'] == DGG.HORIZONTAL: + if self._lastOrientation in (DGG.VERTICAL, DGG.VERTICAL_INVERTED): + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + f = self.decButton['frameSize'] + self.decButton['frameSize'] = (f[2], f[3], f[0], f[1]) + f = self.incButton['frameSize'] + self.incButton['frameSize'] = (f[2], f[3], f[0], f[1]) self.guiItem.setAxis(Vec3(1, 0, 0)) elif self['orientation'] == DGG.VERTICAL: + if self._lastOrientation == DGG.HORIZONTAL: + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + f = self.decButton['frameSize'] + self.decButton['frameSize'] = (f[2], f[3], f[0], f[1]) + f = self.incButton['frameSize'] + self.incButton['frameSize'] = (f[2], f[3], f[0], f[1]) self.guiItem.setAxis(Vec3(0, 0, -1)) elif self['orientation'] == DGG.VERTICAL_INVERTED: + if self._lastOrientation == DGG.HORIZONTAL: + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + f = self.decButton['frameSize'] + self.decButton['frameSize'] = (f[2], f[3], f[0], f[1]) + f = self.incButton['frameSize'] + self.incButton['frameSize'] = (f[2], f[3], f[0], f[1]) self.guiItem.setAxis(Vec3(0, 0, 1)) else: raise ValueError('Invalid value for orientation: %s' % (self['orientation'])) + self._lastOrientation = self['orientation'] def setManageButtons(self): self.guiItem.setManagePieces(self['manageButtons']) diff --git a/direct/src/gui/DirectSlider.py b/direct/src/gui/DirectSlider.py index c5823a9efc..e113f34055 100644 --- a/direct/src/gui/DirectSlider.py +++ b/direct/src/gui/DirectSlider.py @@ -41,7 +41,7 @@ class DirectSlider(DirectFrame): ('extraArgs', [], None), ) - if kw.get('orientation') == DGG.VERTICAL: + if kw.get('orientation') in (DGG.VERTICAL, DGG.VERTICAL_INVERTED): # These are the default options for a vertical layout. optiondefs += ( ('frameSize', (-0.08, 0.08, -1, 1), None), @@ -72,6 +72,8 @@ class DirectSlider(DirectFrame): else: self.thumb['frameSize'] = (f[0], f[1], f[2]*0.05, f[3]*0.05) + self._lastOrientation = self['orientation'] + self.guiItem.setThumbButton(self.thumb.guiItem) # Bind command function @@ -115,11 +117,35 @@ class DirectSlider(DirectFrame): def setOrientation(self): if self['orientation'] == DGG.HORIZONTAL: + if self._lastOrientation in (DGG.VERTICAL, DGG.VERTICAL_INVERTED): + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + tf = self.thumb['frameSize'] + self.thumb['frameSize'] = (tf[2], tf[3], tf[0], tf[1]) self.guiItem.setAxis(Vec3(1, 0, 0)) + self['frameVisibleScale'] = (1, 0.25) elif self['orientation'] == DGG.VERTICAL: + if self._lastOrientation == DGG.HORIZONTAL: + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + tf = self.thumb['frameSize'] + self.thumb['frameSize'] = (tf[2], tf[3], tf[0], tf[1]) self.guiItem.setAxis(Vec3(0, 0, 1)) + self['frameVisibleScale'] = (0.25, 1) + elif self['orientation'] == DGG.VERTICAL_INVERTED: + if self._lastOrientation == DGG.HORIZONTAL: + fpre = self['frameSize'] + # swap frameSize width and height to keep custom frameSizes + self['frameSize'] = (fpre[2], fpre[3], fpre[0], fpre[1]) + tf = self.thumb['frameSize'] + self.thumb['frameSize'] = (tf[2], tf[3], tf[0], tf[1]) + self.guiItem.setAxis(Vec3(0, 0, -1)) + self['frameVisibleScale'] = (0.25, 1) else: raise ValueError('Invalid value for orientation: %s' % (self['orientation'])) + self._lastOrientation = self['orientation'] def destroy(self): if (hasattr(self, 'thumb')): diff --git a/tests/gui/test_DirectSlider.py b/tests/gui/test_DirectSlider.py new file mode 100644 index 0000000000..5c740c6c98 --- /dev/null +++ b/tests/gui/test_DirectSlider.py @@ -0,0 +1,29 @@ +from direct.gui.DirectSlider import DirectSlider +from direct.gui import DirectGuiGlobals as DGG +import pytest + +def test_slider_orientation(): + slider = DirectSlider() + + # Horizontal orientation is the default + assert slider['orientation'] == DGG.HORIZONTAL + assert slider['frameSize'] == (-1, 1, -0.08, 0.08) + assert slider['frameVisibleScale'] == (1, 0.25) + + # try change to vertical orientation + slider['orientation'] = DGG.VERTICAL + assert slider['orientation'] == DGG.VERTICAL + assert slider['frameSize'] == (-0.08, 0.08, -1, 1) + assert slider['frameVisibleScale'] == (0.25, 1) + + # back to horizontal + slider['orientation'] = DGG.HORIZONTAL + assert slider['orientation'] == DGG.HORIZONTAL + assert slider['frameSize'] == (-1, 1, -0.08, 0.08) + assert slider['frameVisibleScale'] == (1, 0.25) + + # finally change to inverted vertical orientation + slider['orientation'] = DGG.VERTICAL_INVERTED + assert slider['orientation'] == DGG.VERTICAL_INVERTED + assert slider['frameSize'] == (-0.08, 0.08, -1, 1) + assert slider['frameVisibleScale'] == (0.25, 1)