I am trying to pass a WX frame class to another class. I have three py files which are as follows:
gui_20220510.py – this contains the gui code
import wx class Frame_Demo(wx.Frame): def __init__(self, *args, **kwds): # begin wxGlade: Frame_Demo.__init__ kwds["style"] = kwds.get("style", 0) | wx.DEFAULT_FRAME_STYLE wx.Frame.__init__(self, *args, **kwds) self.SetSize((400, 300)) self.panel_1 = wx.Panel(self, wx.ID_ANY) sizer_1 = wx.BoxSizer(wx.VERTICAL) self.notebook_1 = wx.Notebook(self.panel_1, wx.ID_ANY) sizer_1.Add(self.notebook_1, 1, wx.EXPAND, 0) self.notebook_1_pane_1 = wx.Panel(self.notebook_1, wx.ID_ANY) self.notebook_1.AddPage(self.notebook_1_pane_1, "notebook_1_pane_1") sizer_2 = wx.BoxSizer(wx.HORIZONTAL) label_1 = wx.StaticText(self.notebook_1_pane_1, wx.ID_ANY, "This is Test: ") sizer_2.Add(label_1, 0, 0, 0) self.text_ctrl_1 = wx.TextCtrl(self.notebook_1_pane_1, wx.ID_ANY, "Type") sizer_2.Add(self.text_ctrl_1, 0, 0, 0) self.notebook_1_pane_2 = wx.Panel(self.notebook_1, wx.ID_ANY) self.notebook_1.AddPage(self.notebook_1_pane_2, "notebook_1_pane_2") sizer_3 = wx.BoxSizer(wx.VERTICAL) sizer_3.Add((0, 0), 0, 0, 0) self.notebook_1_pane_2.SetSizer(sizer_3) self.notebook_1_pane_1.SetSizer(sizer_2) self.panel_1.SetSizer(sizer_1) self.Layout()
demo.py – This contains the run functions to import the wx frame
from importlib import import_module from wx import App global Frame_Demo global builddate class Demo_Main(Frame_Demo): def __init__(self, *args, **kwds): Frame_Demo.__init__(self, *args, **kwds) # Update the Frame Title to Reflect Build Date self.SetTitle('Demo Tool v' + builddate) self.Maximize(True) def main_run(bdate, gui_version): global builddate global Frame_Demo builddate = bdate gui_module = import_module('gui_' + gui_version) Frame_Demo = gui_module.Frame_Demo app = App() frame = Demo_Main(None) frame.Show() app.MainLoop()
Main.py – This is the main file to run the program
from demo import main_run builddate = '2022-MAY-10' gui_version = '20220510' if __name__ == '__main__': main_run(builddate, gui_version)
When trying to run main.py, I am getting “Frame_Demo” is not defined error even though it was defined as a global.
What am I doing wrong here? any guidance is much appreciated. Thanks in advance.
Advertisement
Answer
Word global
is NOT for creating global variables. All variables created outside functions are automtically global (inside current module) but you have to assign value to variable to create it.
We use global
inside function to inform function that when we use =
to assign new value to variable then it has to use external/global variable instead of creating local one.
So you have to import Frame_Demo
before you define class Demo_Main(Frame_Demo):
. Or you have to define this class inside main_run
, after Frame_Demo = gui_module.Frame_Demo
from importlib import import_module from wx import App def main_run(builddate, gui_version): gui_module = import_module('gui_' + gui_version) Frame_Demo = gui_module.Frame_Demo class Demo_Main(Frame_Demo): def __init__(self, *args, **kwds): super().__init__(*args, **kwds) # Update the Frame Title to Reflect Build Date self.SetTitle('Demo Tool v' + builddate) self.Maximize(True) app = App() frame = Demo_Main(None) frame.Show() app.MainLoop()
EDIT:
You could also put these value in separated file – ie. settings.py
builddate = '2022-MAY-10' gui_version = '20220511'
and import it to demo.py
from importlib import import_module from wx import App import settings gui_module = import_module('gui_' + settings.gui_version) Frame_Demo = gui_module.Frame_Demo class Demo_Main(Frame_Demo): def __init__(self, *args, **kwds): super().__init__(*args, **kwds) # Update the Frame Title to Reflect Build Date self.SetTitle('Demo Tool v' + settings.builddate) self.Maximize(True) def main_run(): app = App() frame = Demo_Main(None) frame.Show() app.MainLoop()
And run main.py without these values
from demo import main_run if __name__ == '__main__': main_run()