From e6c2d3b609036724adbdac5dc0cdf802c9a997e2 Mon Sep 17 00:00:00 2001 From: rdb Date: Fri, 23 Feb 2018 22:15:34 +0100 Subject: [PATCH] showbase: allow DirectGui elements to be created before ShowBase This is done by precreating aspect2d inside ShowBaseGlobal. --- direct/src/gui/DirectGuiBase.py | 45 +++++++++++++-------------- direct/src/showbase/ShowBase.py | 12 +++++-- direct/src/showbase/ShowBaseGlobal.py | 4 +++ 3 files changed, 36 insertions(+), 25 deletions(-) diff --git a/direct/src/gui/DirectGuiBase.py b/direct/src/gui/DirectGuiBase.py index 6836f7465f..a0f153d07e 100644 --- a/direct/src/gui/DirectGuiBase.py +++ b/direct/src/gui/DirectGuiBase.py @@ -80,7 +80,8 @@ __all__ = ['DirectGuiBase', 'DirectGuiWidget'] from panda3d.core import * -from panda3d.direct import get_config_showbase +from direct.showbase import ShowBaseGlobal +from direct.showbase.ShowBase import ShowBase from . import DirectGuiGlobals as DGG from .OnscreenText import * from .OnscreenGeom import * @@ -633,7 +634,7 @@ class DirectGuiBase(DirectObject.DirectObject): """ # Need to tack on gui item specific id gEvent = event + self.guiId - if get_config_showbase().GetBool('debug-directgui-msgs', False): + if ShowBase.config.GetBool('debug-directgui-msgs', False): from direct.showbase.PythonUtil import StackTrace print(gEvent) print(StackTrace()) @@ -662,7 +663,7 @@ class DirectGuiWidget(DirectGuiBase, NodePath): # Determine the default initial state for inactive (or # unclickable) components. If we are in edit mode, these are # actually clickable by default. - guiEdit = get_config_showbase().GetBool('direct-gui-edit', 0) + guiEdit = ShowBase.config.GetBool('direct-gui-edit', False) if guiEdit: inactiveInitState = DGG.NORMAL else: @@ -723,21 +724,24 @@ class DirectGuiWidget(DirectGuiBase, NodePath): if self['guiId']: self.guiItem.setId(self['guiId']) self.guiId = self.guiItem.getId() - if __dev__: + + if ShowBaseGlobal.__dev__: guiObjectCollector.addLevel(1) guiObjectCollector.flushLevel() # track gui items by guiId for tracking down leaks - if hasattr(base, 'guiItems'): - if self.guiId in base.guiItems: - base.notify.warning('duplicate guiId: %s (%s stomping %s)' % - (self.guiId, self, - base.guiItems[self.guiId])) - base.guiItems[self.guiId] = self - if hasattr(base, 'printGuiCreates'): - printStack() + if ShowBase.config.GetBool('track-gui-items', True): + if not hasattr(ShowBase, 'guiItems'): + ShowBase.guiItems = {} + if self.guiId in ShowBase.guiItems: + ShowBase.notify.warning('duplicate guiId: %s (%s stomping %s)' % + (self.guiId, self, + ShowBase.guiItems[self.guiId])) + ShowBase.guiItems[self.guiId] = self + # Attach button to parent and make that self - if (parent == None): - parent = aspect2d + if parent is None: + parent = ShowBaseGlobal.aspect2d + self.assign(parent.attachNewNode(self.guiItem, self['sortOrder'])) # Update pose to initial values if self['pos']: @@ -1024,17 +1028,12 @@ class DirectGuiWidget(DirectGuiBase, NodePath): def destroy(self): if hasattr(self, "frameStyle"): - if __dev__: + if ShowBaseGlobal.__dev__: guiObjectCollector.subLevel(1) guiObjectCollector.flushLevel() - if hasattr(base, 'guiItems'): - if self.guiId in base.guiItems: - del base.guiItems[self.guiId] - else: - base.notify.warning( - 'DirectGuiWidget.destroy(): ' - 'gui item %s not in base.guiItems' % - self.guiId) + if hasattr(ShowBase, 'guiItems'): + ShowBase.guiItems.pop(self.guiId, None) + # Destroy children for child in self.getChildren(): childGui = self.guiDict.get(child.getName()) diff --git a/direct/src/showbase/ShowBase.py b/direct/src/showbase/ShowBase.py index 8e3c223000..fd25018634 100644 --- a/direct/src/showbase/ShowBase.py +++ b/direct/src/showbase/ShowBase.py @@ -400,7 +400,8 @@ class ShowBase(DirectObject.DirectObject): if self.__dev__ or self.config.GetBool('want-e3-hacks', False): if self.config.GetBool('track-gui-items', True): # dict of guiId to gui item, for tracking down leaks - self.guiItems = {} + if not hasattr(ShowBase, 'guiItems'): + ShowBase.guiItems = {} # optionally restore the default gui sounds from 1.7.2 and earlier if ConfigVariableBool('orig-gui-sounds', False).getValue(): @@ -520,6 +521,8 @@ class ShowBase(DirectObject.DirectObject): if ShowBaseGlobal: del ShowBaseGlobal.base + self.aspect2d.node().removeAllChildren() + # [gjeon] restore sticky key settings if self.config.GetBool('disable-sticky-keys', 0): allowAccessibilityShortcutKeys(True) @@ -1102,13 +1105,18 @@ class ShowBase(DirectObject.DirectObject): self.render2d.setMaterialOff(1) self.render2d.setTwoSided(1) + # We've already created aspect2d in ShowBaseGlobal, for the + # benefit of creating DirectGui elements before ShowBase. + from . import ShowBaseGlobal + ## The normal 2-d DisplayRegion has an aspect ratio that ## matches the window, but its coordinate system is square. ## This means anything we parent to render2d gets stretched. ## For things where that makes a difference, we set up ## aspect2d, which scales things back to the right aspect ## ratio along the X axis (Z is still from -1 to 1) - self.aspect2d = self.render2d.attachNewNode(PGTop("aspect2d")) + self.aspect2d = ShowBaseGlobal.aspect2d + self.aspect2d.reparentTo(self.render2d) aspectRatio = self.getAspectRatio() self.aspect2d.setScale(1.0 / aspectRatio, 1.0, 1.0) diff --git a/direct/src/showbase/ShowBaseGlobal.py b/direct/src/showbase/ShowBaseGlobal.py index c18ebab5fc..459d5f708f 100644 --- a/direct/src/showbase/ShowBaseGlobal.py +++ b/direct/src/showbase/ShowBaseGlobal.py @@ -11,6 +11,7 @@ from .ShowBase import ShowBase, WindowControls from direct.directnotify.DirectNotifyGlobal import directNotify, giveNotify from panda3d.core import VirtualFileSystem, Notify, ClockObject, PandaSystem from panda3d.core import ConfigPageManager, ConfigVariableManager +from panda3d.core import NodePath, PGTop from panda3d.direct import get_config_showbase config = get_config_showbase() @@ -23,6 +24,9 @@ cpMgr = ConfigPageManager.getGlobalPtr() cvMgr = ConfigVariableManager.getGlobalPtr() pandaSystem = PandaSystem.getGlobalPtr() +# This is defined here so GUI elements can be instantiated before ShowBase. +aspect2d = NodePath(PGTop("aspect2d")) + # Set direct notify categories now that we have config directNotify.setDconfigLevels()