多个面板

3 投票
2 回答
5880 浏览
提问于 2025-04-17 09:44

我在我的程序中遇到了两个问题。下面的代码生成了两个面板,但实际上应该生成三个。它能顺利生成panel1panel2,但是panel3应该在panel2的右边,却完全看不见。panel1panel2是垂直分开的,我想把panel2panel3也做成一样的效果。

我的第二个问题是,如何在panel1下面生成另一个面板,而不影响panel1panel2之间的分隔条,然后再在panel1和新创建的面板之间添加一个分隔条呢?

import wx


class Panels(wx.Frame):
    def __init__(self, parent, id, title):
        wx.Frame.__init__(self, parent, id, title)

        hbox = wx.BoxSizer(wx.HORIZONTAL)
        splitter = wx.SplitterWindow(self, -1)

        vbox1 = wx.BoxSizer(wx.VERTICAL)
        panel1 = wx.Panel(splitter, -1)
        panel12 = wx.Panel(panel1, -1, style=wx.BORDER_SUNKEN)
        st1 = wx.StaticText(panel12, -1, 'Panel 1', (5, 5))
        vbox1.Add(panel12, 1, wx.EXPAND)
        panel1.SetSizer(vbox1)

        vbox2 = wx.BoxSizer(wx.VERTICAL)
        panel2 = wx.Panel(splitter, -1)
        panel22 = wx.Panel(panel2, -1, style=wx.BORDER_RAISED)
        st2 = wx.StaticText(panel22, -1, 'Panel 2', (5, 5))
        vbox2.Add(panel22, 1, wx.EXPAND)
        panel2.SetSizer(vbox2)

        vbox3 = wx.BoxSizer(wx.VERTICAL)
        panel3 = wx.Panel(splitter, -1)
        panel32 = wx.Panel(panel3, -1, style=wx.BORDER_RAISED)
        st3 = wx.StaticText(panel32, -1, 'Panel 3', (5, 5))
        vbox3.Add(panel32, 1, wx.EXPAND)
        panel3.SetSizer(vbox3)

        hbox.Add(splitter, 1, wx.EXPAND | wx.TOP | wx.BOTTOM, 5)
        self.SetSizer(hbox)
        self.CreateStatusBar()
        splitter.SplitVertically(panel1, panel3)
        splitter.SplitVertically(panel2, panel3)
        self.Centre()
        self.Show(True)


    def ExitApp(self, event):
        self.Close()


app = wx.App()
Panels(None, -1, 'Panels')
app.MainLoop()

2 个回答

0

问题1: 创建一个水平的盒子布局(vbox sizer)。把panel2和panel3的布局添加到这个盒子里。这样panel2和panel3就会并排放在一起。接着把这个水平布局作为第二个项目添加到分割器(splitter)里。

问题2: 再创建一个分割器,并把它添加到一个布局里(我假设分割器就像一个面板)。然后创建你的另一个面板,并把它添加到这个分割器里。这样你就把分割器放在了一个布局里面。(不过可能不需要布局也可以。)然后这个布局又在主分割器里面。你可能还可以把第二个分割器放到第一个分割器里面。

5

你有几种选择。你可以把你的分割窗口嵌套起来,这样做虽然有点复杂,但效果不错。或者你可以使用 MultiSplitterWindow 这个小部件。

如果选择第一种方法,我会这样做:

  1. 创建一个主分割器和一个子分割器
  2. 在子分割器里放入前两个面板
  3. 把子分割器和第三个面板放入主分割器里

或者你可以根据这个思路做一些变化。

补充说明:这里有一个例子:

import wx

########################################################################
class RandomPanel(wx.Panel):
    """"""

    #----------------------------------------------------------------------
    def __init__(self, parent, color):
        """Constructor"""
        wx.Panel.__init__(self, parent)
        self.SetBackgroundColour(color)



########################################################################
class MainPanel(wx.Panel):
    """"""

    #----------------------------------------------------------------------
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)

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

        panelOne = RandomPanel(hSplitter, "blue")
        panelTwo = RandomPanel(hSplitter, "red")
        hSplitter.SplitVertically(panelOne, panelTwo)
        hSplitter.SetSashGravity(0.5)

        panelThree = RandomPanel(topSplitter, "green")
        topSplitter.SplitHorizontally(hSplitter, panelThree)
        topSplitter.SetSashGravity(0.5)

        sizer = wx.BoxSizer(wx.VERTICAL)
        sizer.Add(topSplitter, 1, wx.EXPAND)
        self.SetSizer(sizer)

########################################################################
class MainFrame(wx.Frame):
    """"""

    #----------------------------------------------------------------------
    def __init__(self):
        """Constructor"""
        wx.Frame.__init__(self, None, title="Nested Splitters",
                          size=(800,600))
        panel = MainPanel(self)
        self.Show()

#----------------------------------------------------------------------
if __name__ == "__main__":
    app = wx.App(False)
    frame = MainFrame()
    app.MainLoop()

另外,你可能还想看看 wx.SashLayoutWindow:http://www.wxpython.org/docs/api/wx.SashLayoutWindow-class.html

撰写回答