Search code examples
pythonpython-2.7wxpythonwxtextctrl

wxPython textctrl temporarily gets black rectangle


So, I'm trying to write a program using wxPython which will have a notebook with tabs that each have the user enter some data into textboxes. This is for a physics related project so I want each textbox to have a "units" label after it displaying what units it should be entered in. The problem is: When the program runs, I get a black rectangle in the upper left corner of each textctrl which is the size of the label that the units are in. The black box disappears forever immediately after any of the following:

  • press tab onto the textctrl
  • move the cursor onto the textctrl
  • switch tabs in the notebook
  • resize the window until the textctrl has to shrink with it.

functionally everything works fine, I just want to get rid of the black rectangles on startup.

This is my code:

#! usr/bin/python

import wx

class MainWindow(wx.Frame):
    def __init__(self, title):
        wx.Frame.__init__(self, None, title=title, size=(400,300))
        self.make_gui()
        self.Show()

    def make_gui(self):
        self.panel=wx.Panel(self,wx.ID_ANY)
        sizer=wx.BoxSizer(wx.VERTICAL)
        ins=self.gui_inputs()
        sizer.Add(ins)
        self.panel.SetSizer(sizer)

    def gui_inputs(self):
        sizer=wx.BoxSizer(wx.HORIZONTAL)
        simpleinputs=(("Page 1",(("Name",None),("Item","in"))),("sec page",tuple()))
        simple=self.gui_inputs_make_simple(simpleinputs)
        sizer.Add(simple)
        return sizer

    def gui_inputs_make_simple(self,simpleinputs):
        sizer=wx.BoxSizer(wx.VERTICAL)
        notebook=wx.Notebook(self.panel)
        for tab in simpleinputs:
            pan=wx.Panel(notebook,wx.ID_ANY)
            siz=wx.BoxSizer(wx.VERTICAL)
            for item in tab[1]:
                it=self.gui_inputs_make_labeled_unitinput(pan,item[0],item[1])
                siz.Add(it)
            pan.SetSizer(siz)
            notebook.AddPage(pan,tab[0])
        sizer.Add(notebook)
        return sizer

    def gui_inputs_make_labeled_unitinput(self,par,label='',units='',validatenumber=False):
        sizer=wx.BoxSizer(wx.HORIZONTAL)
        lbl=wx.StaticText(par,label=label+':')
        sizer.Add(lbl)
        edit=wx.TextCtrl(par)
        sizer.Add(edit)
        if units!=None:
            unit=wx.StaticText(par,label=units)
            sizer.Add(unit)
        return sizer

app = wx.App(False)
frame = MainWindow("GUI")
app.MainLoop()

and this is a screenshot of what I get:

enter image description here

The following are ways I was able to get the black rectangles to disappear (but none let me do what I need to do):

When I remove the code to put the units in, it works. When I remove the text from the units fields, it works. When I have only one tab, it works.

If anyone can tell me why this is happening, I would be greatly appreciative.

Thanks in advance!


Solution

  • This was an interesting one:

    The black boxes in the TextCtrl instances disappear as soon the sizer cascades are set up properly. You can do this by updating the layout of your main sizer by:

    sizer.Layout()
    

    or

    sizer.Fit(self)
    

    at the end of your make_gui method.

    This works for me but does of course not explain why the TextCtrl stays black in the first place without.