1

我正在尝试构建一个 3 面板 GUI,一切都很顺利,直到我尝试将面板/窗口嵌套在其他面板中并在 GUI 启动时隐藏它们。

看到这张图片...黄色/绿色/蓝色框在初始化期间自动扩展以填充它们的面板,但是在 wx.Panel 初始化期间构建了小紫色框但随后隐藏,直到 2 秒计时器到期然后在那个时候该对象的 Show() 方法被调用。那时它不会填满包含面板。似乎在初始化期间隐藏面板会导致面板大小调整器选择默认大小 20x20。

尺寸测试

这是代码:

import wx
import  wx.lib.scrolledpanel as scrolled

class NavPanel(wx.Panel):
    """"""
    def __init__(self, parent, actionPanel):
        """Constructor"""
        wx.Panel.__init__(self, parent) #, size=(200,600))
        self.actionPanel = actionPanel
        self.SetBackgroundColour("Yellow")

class ActionPanel(wx.Panel):
    """"""
    def __init__(self, parent, target_item=None):
        """Constructor"""
        wx.Panel.__init__(self, parent)
        self.SetBackgroundColour("Green")

        self.sc = NestedScrolledActionPanel(self)

        sizer = wx.BoxSizer(wx.HORIZONTAL)
        sizer.Add(self.sc, 1, wx.EXPAND)
        self.SetSizer(sizer)

    def show_child(self):
        # Putting a sizer here doesn't work either...
        self.sc.Show()


class NestedScrolledActionPanel(wx.ScrolledWindow):
    """"""
    def __init__(self, parent, target_item=None):
        """Constructor"""
        wx.ScrolledWindow.__init__(self, parent)
        self.SetBackgroundColour("Purple")

        # I don't want to show this at starutp, but hiding it causes the sizer to startup at 20x20!
        # Comment out this line and the sizer set in ActionPanel works, but you see it at startup
        self.Hide()       

class ConsolePanel(scrolled.ScrolledPanel): 
    """"""
    def __init__(self, parent):
        """Constructor"""

        scrolled.ScrolledPanel.__init__(self, parent, -1)
        self.SetBackgroundColour("Blue")

class MainPanel(wx.Panel):
    """"""
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)

        mainSplitter = wx.SplitterWindow(self)
        topSplitter = wx.SplitterWindow(mainSplitter)

        self.rightPanel = ActionPanel(topSplitter)
        self.rightPanel.SetBackgroundColour("Green")

        leftPanel = NavPanel(topSplitter, self.rightPanel)
        leftPanel.SetBackgroundColour("Yellow")

        topSplitter.SplitVertically(leftPanel, self.rightPanel, sashPosition=0)
        topSplitter.SetMinimumPaneSize(200)

        bottomPanel = ConsolePanel(mainSplitter)

        mainSplitter.SplitHorizontally(topSplitter, bottomPanel, sashPosition=400)
        mainSplitter.SetSashGravity(1)

        sizer = wx.BoxSizer(wx.HORIZONTAL)
        sizer.Add(mainSplitter, 1, wx.EXPAND)
        self.SetSizer(sizer)

        return


########################################################################
class MainFrame(wx.Frame):
    """"""
    def __init__(self):
        """Constructor"""

        wx.Frame.__init__(self, None, title="Sizer Test",
                          size=(800,600))

        self.panel = MainPanel(self)

        self.Centre()
        self.Show()

        self.timer = wx.Timer(self)
        self.Bind(wx.EVT_TIMER, self.OnTimer, self.timer)
        self.timer.Start(2000)

    def OnTimer(self, e):
        self.panel.rightPanel.show_child()

if __name__ == '__main__':
    app = wx.App(redirect=False)
    print "Launching frame"
    frame = MainFrame()
    print "starting mainloop"
    app.MainLoop()

我希望在 GUI 启动时隐藏此面板的原因是因为我将在该 ActionPanel 空间(绿色框)中有许多不同的面板,并且当用户单击黄色框中的树节点时,显示在将隐藏绿色框并显示不同的面板。如果我在启动时不隐藏所有面板,它们会“堆叠”在彼此之上,我将不得不设置一个计时器来通过并在 GUI 启动后的某个时间点将它们全部隐藏???这似乎很胡扯。我还能怎么做?

4

2 回答 2

1

添加self.Layout()到您的 show_child 方法。仅显示孩子不会像 size 事件那样触发布局。对于那些需要在没有大小事件的情况下更改布局的时候,您需要自己调用 Layout。

于 2013-02-04T19:55:35.610 回答
0

我为 Stack Overflow 构建了一个简单的案例经历了很多麻烦,但这只暴露了第二个问题,RobinDunn 回答了这个问题。我的另一个更令人抓狂的问题是我试图向一个对象添加两个 sizer。只有最后一个有sizer,其余的是20x20,我想不通。

我希望两个不同的面板在不同的时间共享同一个父面板,所以我这样做了......(未经测试的代码)..

some_object= wx.Panel(self)  # Could be anything
sizer = BoxSizer(wx.VERTICAL)
sizer.Add(some_object, 1, wx.EXPAND)
sizer.SetSizer(sizer)

something_else = wx.Panel(self)  # Could be anything
something_else.Hide()
sizer = BoxSizer(wx.VERTICAL)
sizer.Add(something_else, 1, wx.EXPAND)
sizer.SetSizer(sizer)

但我应该做的是:

some_object= wx.Panel(self)  # Could be anything
something_else = wx.Panel(self)  # Could be anything
something_else.Hide()
sizer = BoxSizer(wx.VERTICAL)
sizer.Add(some_object, 1, wx.EXPAND)
sizer.Add(something_else, 1, wx.EXPAND)
sizer.SetSizer(sizer)

然后,当然,在每次显示/隐藏不同面板后执行 Layout() 操作,以及 36 小时的头疼之后,我已经痊愈了!

于 2013-02-06T06:51:43.127 回答