【问题标题】:wxpython boxsizer:problems with dynamically adding itemswxpython boxsizer:动态添加项目的问题
【发布时间】:2012-08-22 12:42:47
【问题描述】:

这让我发疯了。我通常将 Tkinter 用于 gui 的东西,但只是觉得实际上是在尝试学习 wxpython。

我终其一生都无法弄清楚为什么当我使用 boxsizer 将按钮或静态文本等项目添加到面板时。它似乎将所有内容都塞进了名为“side”的面板上的位置(0,0),这是我的代码。

    import wx

    def AddUser():
        ex = wx.App()
        Stylex = wx.SYSTEM_MENU|wx.CAPTION|wx.CLOSE_BOX
        window = wx.Frame(None, style=Stylex)

        splitter = wx.SplitterWindow(window, -1)
        vbox = wx.BoxSizer(wx.VERTICAL)
        """
        LEFT PANEL... Contains Navigation Tree
        """
        fgs = wx.FlexGridSizer(2,1,5,10) # fgs(int rows, int cols, int vgap, int hgap

        panel = wx.Panel(splitter, -1)
        panel.SetBackgroundColour('#ededed')

        side = wx.Panel(splitter, -1)
        side.SetBackgroundColour('#4f5049')

        multi_btn = wx.Button(panel, label="Batch User Mode")
        multi_btn.SetId(50)

        single_btn = wx.Button(panel, label="Single User Mode")
        single_btn.SetId(25)

        items = [multi_btn,single_btn]

        fgs.AddMany(items)
        vbox.Add(fgs)

        panel.SetSizer(vbox)
        splitter.SplitVertically(panel, side,100)

        """
        SIDE panel...  Contains all widgets
        """
        st = wx.StaticText(side, label="Select a Mode", pos=wx.Point(20,100))
        st.SetForegroundColour(wx.WHITE)

        def SetMode(event):
            """
            25 returned if Single user mode
            50 returned if Batch user mode
            """
            MODE = event.GetId()

            if MODE == 25:
                try:
                    side.DestroyChildren()
                except: pass

                """
                Problem adding items to the dynamnic changing 'SIDE' panel
                """
                vb = wx.BoxSizer(wx.VERTICAL)

                stFName = wx.StaticText(side, id=2,label="First Name:")
                stFName.SetForegroundColour(wx.WHITE)
                vb.Add(stFName)
                tcFName = wx.TextCtrl(side, id=4)
                vb.Add(tcFName)

                stLName = wx.StaticText(side,id=6, label="Last Name:")
                vb.Add(stLName)
                tcLName = wx.TextCtrl(side, id=8)
                vb.Add(tcLName)

                vb.Add(side, 1, flag=wx.EXPAND|wx.ALL, border=5)

                side.SetSizer(vb)

                """
                END Problem
                """
            if MODE == 50:
                try:
                    side.DestroyChildren()
                except: pass
                """
                do the same thing as single user creation, except adding listboxes instead of textctrl's
                """
            return

        multi_btn.Bind(wx.EVT_BUTTON, SetMode)
        single_btn.Bind(wx.EVT_BUTTON, SetMode)

        window.SetTitle('User Creation Process')
        window.Centre()
        window.Show(True)

        ex.MainLoop()

    if __name__=='__main__':
        AddUser()

非常感谢您的帮助...我确定这是我忽略的一些小问题,但我想了解它是否是一个基本问题。

兰迪

【问题讨论】:

  • 我刚刚注意到您将side 添加到vb,然后将vb 设置为side 的sizer。所以vb 包含side,其中包含vb,其中包含side,其中包含...我的头疼。如果您side 添加到vb 会发生什么?
  • 嘿,谢谢@acattle 我删除了vb.Add(side, 1, flag=wx.EXPAND|wx.ALL, border=5) 的部分,但它似乎没有帮助......这告诉我我可以把它排除在代码之外?整件事让我头疼。哈哈

标签: user-interface wxpython boxsizer


【解决方案1】:

这是默认位置。 Sizer 不适用于绝对定位。如果你愿意,你可以通过在每个小部件中传递一个位置来做到这一点。如果您希望您的小部件在左侧居中,那么您需要将垂直 BoxSizer 放在水平的 BoxSizer 内并将其居中。或者,您可以使用 AddSpacer 或仅添加大小来使用几个 Spacers:

mySizer.Add((10, 20), 0, wx.ALL, 5)

您还可以使用 Sizer 的 Add 方法的“border”参数在一定程度上控制布局,使用 wx.TOP、wx.BOTTOM、wx.RIGHT 或 wx.LEFT 并为其提供适当的空间量。如果您看到小部件堆叠在一起,那么您需要在最后添加一个 Layout 调用(可能来自面板或框架)。

更新:如果您想更换面板,我建议您只隐藏和显示它们或销毁和创建面板。我写了一个关于切换面板的教程,可能会有所帮助:http://www.blog.pythonlibrary.org/2010/06/16/wxpython-how-to-switch-between-panels/

【讨论】:

  • OP 不使用 sizer 来设置绝对位置。他们在初始化期间设置了一个绝对位置,但在将内容添加到 sizer 之前,他们会破坏面板的所有子项。
  • 我没有看到任何定位,但我一定错过了它。
  • 谢谢@MikeDriscoll 我还没有让它工作,但我一定会看那个教程。理想情况下,我不想使用绝对定位,但我试图花哨并使 StaticText(“st”)浮动到一个新位置......我认为我的下一步是做更多的教程,我只是认为它应该很简单...... side... which is already there 然后你设置你的boxsizer 然后你添加你的wx.Buttons and wx.StaticTexts to your boxsizer 然后你的panel sets the boxsizer
  • 你知道...做一个绝对位置并不是世界末日...我可以让它工作,我在每个之后都包括 mySizers...网格我猜你可以调用它。我认为我的部分问题是我在想我可以将我创建的所有项目添加到 1 个垂直 boxsizer 中而不使用任何水平尺寸器......相反,我认为我应该专注于将项目放入网格中。
  • 是的,当您限制用户调整框架大小的能力时,绝对定位没有任何问题。否则,布局可能看起来有点奇怪。我仍然认为你可以用一些垫片和一些更大的嵌套来做你想做的事,但有时当你刚刚学习 wxPython 时这可能会很痛苦。
猜你喜欢
  • 2021-06-14
  • 1970-01-01
  • 1970-01-01
  • 2018-10-01
  • 2019-03-25
  • 1970-01-01
  • 2013-07-28
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多