【问题标题】:wxPython Sizer set fixed height for panelwxPython Sizer 为面板设置固定高度
【发布时间】:2020-05-26 02:35:52
【问题描述】:

我对 wxPython 非常陌生,并且正在学习如何使用 sizer。我已经成功创建了一个似乎正确对齐的面板,但是我想在它的正下方放置一个新面板,并且在那里遇到了问题。我希望第一个具有绿色背景的面板具有固定的高度,但绿色背景填充了整个框架,即使面板的内容似乎按照我想要的方式排列在其中。感谢您的帮助。

这是一张最大化框架以填满我的窗口的图片:

这只是一个面板。面板的内容沿顶部正确对齐,但是我希望面板在这些小部件下方停止,以便我可以启动一个新面板。所以绿色不应该填满整个窗口,因为我已经将此框架的背景设置为绿色。绿色应该在小部件下方停止,然后我想添加另一个框架。

这是我的完整代码:

import time
import os
import gc
import wx
import wx.grid

# wxpython app
# read ss from files or live version
class Wx_app(wx.App):

    # __init__ gets called first when any class is initialized
    def __init__(self):

    # intiialize the App window
    super().__init__(clearSigInt=True)

    # don't set size of the frame, just position. let 
    # sizers do the sizing?
    self.frame = MyFrame(None, pos=(10,10))

# frame class (wx python wind)
class MyFrame(wx.Frame):

    def __init__(self, *args, **kwargs):

        # ini the frame and show it
        super(MyFrame, self).__init__(*args, **kwargs)

        # main sizer, will contain all of the other sizers
        self.main_sizer = wx.BoxSizer(wx.VERTICAL)

        # FONTS
        # font to use for the panel in labels, text ctrls, etc
        txt_font = wx.Font(18, wx.DEFAULT, wx.NORMAL, wx.NORMAL)
        # font to use for buttons is slightly small than txt_font
        but_font = wx.Font(15, wx.DEFAULT, wx.NORMAL, wx.NORMAL)

        # PANEL 1
        # first panel is at the top, contains manual pick area plus msg area
        self.pick_area_panel = PickAreaPanel(self, txt_font, but_font)
        self.main_sizer.Fit(self.pick_area_panel)


        # show the frame with panel
        self.Show(True)

# panel class
class PickAreaPanel(wx.Panel):

    def __init__(self, parent, txt_font, but_font):

        # ini
        super().__init__(parent=parent)

        # set background colour for panel
        self.SetBackgroundColour("Green")

        # create the sizer for this panel.
        # stuff is organized horizontally left to right
        self.panel_sizer = wx.BoxSizer(wx.HORIZONTAL)

        # NOTE: By setting width to -1, we tell to go with sizer, and height to 100
        # sets a fixed height
        pick_label = wx.StaticText(self, -1, "Confirm Pick R1 P1: ", size=(240, 25))
        pick_label.SetBackgroundColour("Red")
        pick_label.SetFont(txt_font)

        # input textctrl for the manual pick
        pick_input = wx.TextCtrl(self, -1, size=(320, 25))
        pick_input.SetFont(txt_font)

        # button to confirm manual pick
        pick_confirm_but = wx.Button(self, -1, size=(150, 25))
        pick_confirm_but.SetLabel("Confirm")
        pick_confirm_but.SetFont(but_font)

        # PROG MSG AREA
        # no fixed size, fills rest of panel after previous elements
        # need a nested sizer so can control borders
        # and give it a left borcer thats different from its top border
        prog_msg_area_sizer = wx.BoxSizer(wx.HORIZONTAL)
        prog_msg_area = wx.StaticText(self, -1, "MSG MSG MSG", size=(-1, 25), style=wx.ALIGN_CENTER)
        prog_msg_area.SetBackgroundColour("White")
        prog_msg_area.SetFont(txt_font)
        prog_msg_area_sizer.Add(prog_msg_area, proportion=1, flag=wx.EXPAND|wx.TOP, border=0)

        # add elements to panel sizer
        self.panel_sizer.Add(pick_label, proportion=0, flag=wx.EXPAND|wx.TOP, border=3)
        self.panel_sizer.Add(pick_input, proportion=0, flag=wx.EXPAND)
        self.panel_sizer.Add(pick_confirm_but, proportion=0, flag=wx.EXPAND)
        # prog msg area has its own horiz sizer so can set a left border diff from top border 
        self.panel_sizer.Add(prog_msg_area_sizer, proportion=1, flag=wx.EXPAND|wx.LEFT, border=10)

        # add panel sizer to the main sizer
        # set proporition to 0 so height of panel doesnt change when height of frame changes
        # adds a border around the entire panel
        parent.main_sizer.Add(self.panel_sizer, proportion=0, flag=wx.EXPAND|wx.ALL, border=15)

        # set panel to use the main sizer
        # not sure exactly how this works....
        self.SetSizer(parent.main_sizer)

wx_app = Wx_app()       
if __name__ == '__main__':
    wx_app.MainLoop()

建议更改的编辑程序

import time
import os
import gc
import wx
import wx.grid

class Wx_app(wx.App):

    def __init__(self):

    super().__init__(clearSigInt=True)

    self.frame = MyFrame(None, pos=(10,10))

class MyFrame(wx.Frame):

    def __init__(self, *args, **kwargs):

        super(MyFrame, self).__init__(*args, **kwargs)

        self.main_sizer = wx.BoxSizer(wx.VERTICAL)

        txt_font = wx.Font(18, wx.DEFAULT, wx.NORMAL, wx.NORMAL)
        but_font = wx.Font(15, wx.DEFAULT, wx.NORMAL, wx.NORMAL)

        self.pick_area_panel = PickAreaPanel(self, txt_font, but_font)

        # *******ADDED:
        self.SetSizer(self.main_sizer)

        self.Show(True)

# panel class
class PickAreaPanel(wx.Panel):

    def __init__(self, parent, txt_font, but_font):

        super().__init__(parent=parent)

        self.SetBackgroundColour("Green")

        self.panel_sizer = wx.BoxSizer(wx.HORIZONTAL)

        pick_label = wx.StaticText(self, -1, "Confirm Pick R1 P1: ", size=(240, 25))
        pick_label.SetBackgroundColour("Red")
        pick_label.SetFont(txt_font)

        pick_input = wx.TextCtrl(self, -1, size=(320, 25))
        pick_input.SetFont(txt_font)

        pick_confirm_but = wx.Button(self, -1, size=(150, 25))
        pick_confirm_but.SetLabel("Confirm")
        pick_confirm_but.SetFont(but_font)

        prog_msg_area_sizer = wx.BoxSizer(wx.HORIZONTAL)
        prog_msg_area = wx.StaticText(self, -1, "MSG MSG MSG", size=(-1, 25), style=wx.ALIGN_CENTER)
        prog_msg_area.SetBackgroundColour("White")
        prog_msg_area.SetFont(txt_font)
        prog_msg_area_sizer.Add(prog_msg_area, proportion=1, flag=wx.EXPAND|wx.TOP, border=0)


        self.panel_sizer.Add(pick_label, proportion=0, flag=wx.EXPAND|wx.TOP, border=3)
        self.panel_sizer.Add(pick_input, proportion=0, flag=wx.EXPAND)
        self.panel_sizer.Add(pick_confirm_but, proportion=0, flag=wx.EXPAND)
        self.panel_sizer.Add(prog_msg_area_sizer, proportion=1, flag=wx.EXPAND|wx.LEFT, border=10)

        parent.main_sizer.Add(self.panel_sizer, proportion=0, flag=wx.EXPAND|wx.ALL, border=15)

        # CHANGED
        self.SetSizer(self.panel_sizer)

wx_app = Wx_app()       
if __name__ == '__main__':
    wx_app.MainLoop()

【问题讨论】:

  • 将panel sizer设置为panel的sizer,main sizer设置为frame的sizer。在“MyFrame”构造函数中更好地将面板添加到主尺寸器(不是必需的,但更合乎逻辑)并且不要调用“Fit”。
  • 感谢您的回复。我做了你建议的改变(我认为),现在我只看到框架左上角有一个绿色的小方块。我编辑了代码以显示我的更改。您能否更具体地说明为什么这不起作用谢谢。
  • 我能给你的最好的建议:为 wxpython 使用 WXGLADE。它修复了您的生活,并且您可以通过查看生成的干净代码来学习很多 WXPython。
  • 我监督您将 panel sizer 添加到 main sizer。相反,您应该将面板本身添加到主尺寸器。

标签: python wxpython


【解决方案1】:

我从未尝试将一个类的 sizer 设置为另一个类的 sizer,这就是您在这里所做的。
为面板设置尺寸器,并为框架单独设置尺寸器。 见下文:您会注意到我制作了面板的副本以说明框架中的 2 个面板。

import time
import os
import gc
import wx
import wx.grid

# wxpython app
# read ss from files or live version
class Wx_app(wx.App):

    # __init__ gets called first when any class is initialized
    def __init__(self):

    # intiialize the App window
        super().__init__(clearSigInt=True)

        # don't set size of the frame, just position. let
        # sizers do the sizing?
        self.frame = MyFrame(None, pos=(10,10))

# frame class (wx python wind)
class MyFrame(wx.Frame):

    def __init__(self, *args, **kwargs):

        # ini the frame and show it
        super(MyFrame, self).__init__(*args, **kwargs)

        # main sizer, will contain all of the other sizers
        self.main_sizer = wx.BoxSizer(wx.VERTICAL)

        # FONTS
        # font to use for the panel in labels, text ctrls, etc
        txt_font = wx.Font(18, wx.DEFAULT, wx.NORMAL, wx.NORMAL)
        # font to use for buttons is slightly small than txt_font
        but_font = wx.Font(15, wx.DEFAULT, wx.NORMAL, wx.NORMAL)

        # PANEL 1
        # first panel is at the top, contains manual pick area plus msg area
        self.pick_area_panel = PickAreaPanel(self, txt_font, but_font)
        self.pick_area_panel2 = PickAreaPanel(self, txt_font, but_font)
        self.main_sizer.Add(self.pick_area_panel, proportion=0, flag=wx.EXPAND|wx.ALL, border=10)
        self.main_sizer.Add(self.pick_area_panel2, proportion=0, flag=wx.EXPAND|wx.ALL, border=10)
        self.SetSizerAndFit(self.main_sizer)

        # show the frame with panel
        self.Show(True)

# panel class
class PickAreaPanel(wx.Panel):

    def __init__(self, parent, txt_font, but_font):

        # ini
        super().__init__(parent=parent)

        # set background colour for panel
        self.SetBackgroundColour("Green")

        # create the sizer for this panel.
        # stuff is organized horizontally left to right
        self.panel_sizer = wx.BoxSizer(wx.HORIZONTAL)

        # NOTE: By setting width to -1, we tell to go with sizer, and height to 100
        # sets a fixed height
        pick_label = wx.StaticText(self, -1, "Confirm Pick R1 P1: ", size=(240, 25))
        pick_label.SetBackgroundColour("Red")
        pick_label.SetFont(txt_font)

        # input textctrl for the manual pick
        pick_input = wx.TextCtrl(self, -1, size=(320, 25))
        pick_input.SetFont(txt_font)

        # button to confirm manual pick
        pick_confirm_but = wx.Button(self, -1, size=(150, 25))
        pick_confirm_but.SetLabel("Confirm")
        pick_confirm_but.SetFont(but_font)

        # PROG MSG AREA
        # no fixed size, fills rest of panel after previous elements
        # need a nested sizer so can control borders
        # and give it a left borcer thats different from its top border
        prog_msg_area_sizer = wx.BoxSizer(wx.HORIZONTAL)
        prog_msg_area = wx.StaticText(self, -1, "MSG MSG MSG", size=(-1, 25), style=wx.ALIGN_CENTER)
        prog_msg_area.SetBackgroundColour("White")
        prog_msg_area.SetFont(txt_font)
        prog_msg_area_sizer.Add(prog_msg_area, proportion=1, flag=wx.EXPAND|wx.TOP, border=0)

        # add elements to panel sizer
        self.panel_sizer.Add(pick_label, proportion=0, flag=wx.EXPAND|wx.TOP, border=3)
        self.panel_sizer.Add(pick_input, proportion=0, flag=wx.EXPAND)
        self.panel_sizer.Add(pick_confirm_but, proportion=0, flag=wx.EXPAND)
        # prog msg area has its own horiz sizer so can set a left border diff from top border
        self.panel_sizer.Add(prog_msg_area_sizer)

        # add panel sizer to the main sizer
        # set proporition to 0 so height of panel doesnt change when height of frame changes
        # adds a border around the entire panel
        #parent.main_sizer.Add(self.panel_sizer, proportion=0, flag=wx.ALL, border=15)

        # set panel to use the main sizer
        # not sure exactly how this works....
        self.SetSizer(self.panel_sizer)

wx_app = Wx_app()
if __name__ == '__main__':
    wx_app.MainLoop()

【讨论】:

    猜你喜欢
    • 2010-10-18
    • 2012-12-10
    • 1970-01-01
    • 2021-06-09
    • 2020-03-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多