Crash when trying to get parent of wxPanel

BlitzMax Forums/Brucey's Modules/Crash when trying to get parent of wxPanel

rs22(Posted 2010) [#1]
Hi,

I can't seem to figure this out. When I try to get the parent of a wxPanel, it goes boom. In my app, I have a group of toggle buttons parented to a panel, and I need to get the parent of that panel, which is the dialog box so I can parent requesters and such to it.

SuperStrict

Framework wx.wxApp
Import wx.wxButton
Import wx.wxFrame
Import wx.wxPanel
Import wx.wxBitmapToggleButton

Const wxID_TOGGLE1:Int = wxID_HIGHEST + 1
Const wxID_TOGGLE2:Int = wxID_HIGHEST + 2

Type MyApp Extends wxApp
	Field frame:MyFrame
	Method OnInit:Int()
		frame = MyFrame(New MyFrame.Create(,,"Minimal wxWidgets App", 100, 100))
		SetTopWindow(frame)		
		frame.show()		
		Return True	
	EndMethod
EndType

Type MyFrame Extends wxFrame

	Field m_toggleBtn1:wxBitmapToggleButton
	Field m_panel1:wxPanel
	Field m_toggleBtn4:wxBitmapToggleButton


	Method OnInit()
	
		Local bmp:wxBitmap = New wxBitmap.CreateEmpty(16, 16)
		bmp.Colourize(New wxColour.Create(255, 0, 0))
	
		Local gSizer1:wxGridSizer
		gSizer1 = New wxGridSizer.CreateRC(1, 2, 0, 0)
		m_toggleBtn1 = New wxBitmapToggleButton.Create(Self, wxID_TOGGLE1, bmp)

		gSizer1.Add(m_toggleBtn1, 0, wxALL, 5)

		m_panel1 = New wxPanel.Create(Self, wxID_ANY,,,,, wxTAB_TRAVERSAL)

		Local bSizer1:wxBoxSizer
		bSizer1 = New wxBoxSizer.Create(wxVERTICAL)

		m_toggleBtn4 = New wxBitmapToggleButton.Create(m_panel1, wxID_TOGGLE2, bmp)

		bSizer1.Add(m_toggleBtn4, 0, wxALL, 5)

		m_panel1.SetSizer(bSizer1)
		m_panel1.Layout()
		bSizer1.Fit(m_panel1)
		gSizer1.Add(m_panel1, 1, wxEXPAND | wxALL, 5)

		SetSizer(gSizer1)
		Layout()
		
		Connect(wxID_EXIT, wxEVT_COMMAND_MENU_SELECTED, OnQuit)
		
		Connect(wxID_TOGGLE1, wxEVT_COMMAND_BUTTON_CLICKED, OnToggle1)
		Connect(wxID_TOGGLE2, wxEVT_COMMAND_TOGGLEBUTTON_CLICKED, OnToggle2)
		
	End Method
	
	Function OnToggle1(event:wxEvent)
		Local btn:wxButton = wxButton(event.parent)
		Local frame:MyFrame = MyFrame(btn.GetParent())
		event.skip()
	EndFunction
	
	Function OnToggle2(event:wxEvent)
		Local btn:wxToggleButton = wxToggleButton(event.parent)
		Local panel:wxPanel = wxPanel(btn.GetParent())
		Local frame:MyFrame = MyFrame(panel.GetParent())
	EndFunction

	Function OnQuit(event:wxEvent)
		' true is to force the frame to close
		wxWindow(event.parent).Close(True)
	EndFunction
	
EndType

New MyApp.Run()

Am I doing something wrong?


Brucey(Posted 2010) [#2]
Am I doing something wrong?

Yes.

Your problem is that wxToggleButton(event.parent) returns Null, and your code is crashing because you are trying to call a method on a Null object.

That's because the event parent, is the wxFrame.
When you Connect() an event, the "parent" will be the object to which you connected. So, in your case your event handler is connected to the instance of MyFrame.

There are two ways you can get the functionality you are after.

1) You add a an event sink parameter of the button, which you can access via event.sink :
Connect(wxID_TOGGLE2, wxEVT_COMMAND_TOGGLEBUTTON_CLICKED, OnToggle2, Null, m_toggleBtn4)


2) You connect to the button itself, and pass the parent as the sink, where parent will be the button, and sink will be the frame :
m_toggleBtn1.Connect(wxID_TOGGLE1, wxEVT_COMMAND_TOGGLEBUTTON_CLICKED, OnToggle1, Null, Self)



rs22(Posted 2010) [#3]
Haha, thanks. I figured it was me being stupid. I always thought the parent of the event was the control it came from and was connected to. I didn't know about any of the 'sink' stuff either.

Thanks a lot!