I've been working with python for a while now and am just starting to learn wxPython. After creating a few little programs, I'm having difficulty understanding how to create objects that can be shared between dialogs.
Here's some code as an example (apologies for the length - I've tried to trim):
import wx
class ExampleFrame(wx.Frame):
"""The main GUI"""
def __init__(self, parent, id, title):
wx.Frame.__init__(self, parent, id, title, size=(200,75))
mainSizer = wx.BoxSizer(wx.VERTICAL)
# Setup buttons
buttonSizer = wx.BoxSizer(wx.HORIZONTAL)
playerButton = wx.Button(self, wx.ID_ANY, "Player number", wx.DefaultPosition, wx.DefaultSize, 0)
buttonSizer.Add(playerButton, 1, wx.ALL | wx.EXPAND, 0)
nameButton = wx.Button(self, wx.ID_ANY, "Player name", wx.DefaultPosition, wx.DefaultSize, 0)
buttonSizer.Add(nameButton, 1, wx.ALL | wx.EXPAND, 0)
# Complete layout and add statusbar
mainSizer.Add(buttonSizer, 1, wx.EXPAND, 5)
self.SetSizer(mainSizer)
self.Layout()
# Deal with the events
playerButton.Bind(wx.EVT_BUTTON, self.playerButtonEvent)
nameButton.Bind(wx.EVT_BUTTON, self.nameButtonEvent)
self.Show(True)
return
def playerButtonEvent(self, event):
"""Displays the number of game players"""
playerDialog = PlayerDialogWindow(None, -1, "Player")
playerDialogResult = playerDialog.ShowModal()
playerDialog.Destroy()
return
def nameButtonEvent(self, event):
"""Displays the names of game players"""
nameDialog = NameDialogWindow(None, -1, "Name")
nameDialogResult = nameDialog.ShowModal()
nameDialog.Destroy()
return
class PlayerDialogWindow(wx.Dialog):
"""Displays the player number"""
def __init__(self, parent, id, title):
wx.Dialog.__init__(self, parent, id, title, size=(200,120))
# Setup layout items
self.SetAutoLayout(True)
mainSizer = wx.BoxSizer(wx.VERTICAL)
dialogPanel = wx.Panel(self, wx.ID_ANY, wx.DefaultPosition, wx.DefaultSize, wx.TAB_TRAVERSAL)
dialogSizer = wx.BoxSizer(wx.VERTICAL)
# Display player number
playerNumber = "Player number is %i" % gamePlayer.number
newLabel = wx.StaticText(dialogPanel, wx.ID_ANY, playerNumber, wx.DefaultPosition, wx.DefaultSize, 0)
dialogSizer.Add(newLabel, 0, wx.ALL | wx.EXPAND, 5)
# Setup buttons
buttonSizer = wx.StdDialogButtonSizer()
okButton = wx.Button(dialogPanel, wx.ID_OK)
buttonSizer.AddButton(okButton)
buttonSizer.Realize()
dialogSizer.Add(buttonSizer, 1, wx.EXPAND, 5)
# Complete layout
dialogPanel.SetSizer(dialogSizer)
dialogPanel.Layout()
dialogSizer.Fit(dialogPanel)
mainSizer.Add(dialogPanel, 1, wx.ALL | wx.EXPAND, 5)
self.SetSizer(mainSizer)
self.Layout()
# Deal with the button events
okButton.Bind(wx.EVT_BUTTON, self.okClick)
return
def okClick(self, event):
"""Deals with the user clicking the ok button"""
self.EndModal(wx.ID_OK)
return
class NameDialogWindow(wx.Dialog):
"""Displays the player name"""
def __init__(self, parent, id, title):
wx.Dialog.__init__(self, parent, id, title, size=(200,120))
# Setup layout items
self.SetAutoLayout(True)
mainSizer = wx.BoxSizer(wx.VERTICAL)
dialogPanel = wx.Panel(self, wx.ID_ANY, wx.DefaultPosition, wx.DefaultSize, wx.TAB_TRAVERSAL)
dialogSizer = wx.BoxSizer(wx.VERTICAL)
# Display player number
playerNumber = "Player name is %s" % gamePlayer.name
newLabel = wx.StaticText(dialogPanel, wx.ID_ANY, playerNumber, wx.DefaultPosition, wx.DefaultSize, 0)
dialogSizer.Add(newLabel, 0, wx.ALL | wx.EXPAND, 5)
# Setup buttons
buttonSizer = wx.StdDialogButtonSizer()
okButton = wx.Button(dialogPanel, wx.ID_OK)
buttonSizer.AddButton(okButton)
buttonSizer.Realize()
dialogSizer.Add(buttonSizer, 1, wx.EXPAND, 5)
# Complete layout
dialogPanel.SetSizer(dialogSizer)
dialogPanel.Layout()
dialogSizer.Fit(dialogPanel)
mainSizer.Add(dialogPanel, 1, wx.ALL | wx.EXPAND, 5)
self.SetSizer(mainSizer)
self.Layout()
# Deal with the button events
okButton.Bind(wx.EVT_BUTTON, self.okClick)
return
def okClick(self, event):
"""Deals with the user clicking the ok button"""
self.EndModal(wx.ID_OK)
return
class Player(object):
"""A game player"""
def __init__(self, number, name):
self.number = number
self.name = name
return
def main():
# Start GUI
global gamePlayer
gamePlayer = Player(1, "John Smith")
app = wx.App(redirect=False)
frame = ExampleFrame(None, -1, "Example frame")
frame.Show(True)
app.MainLoop()
return 0
if __name__ == '__main__':
main()
So, I want both of the dialogs to access the gamePlayer object. At the moment, the only way I can think of doing it is to create the gamePlayer object as a global object, but these are normally frowned upon - is there a better way to do this?
There is a method of passing objects in event bindings in this question, but it doesn't feel quite right.
Is learning to implement the MVC pattern the way forward here?
Thanks.