kdottiemo
kdottiemo

Reputation: 79

wxWidgets Event-Propagation from Dialogs in C++

I am relatively new to GUI programming with wxWidgets. Lately, I have been frustrated that the default behavior for event-propagation in the context of dialog boxes is to not automatically propagate events back to the parents. Documentation says something like "there will probably be too many dialog box events to keep track of." I am using event tables for events, not Connect()....yet, anyway.

I have a bunch of radio buttons on a dialog that gets popped up on top of a wxPanel. When the user selects a radio button, I want the information about which button is selected to propagate back to the wxPanel. The choice of this button decides something that happens to the image that has been loaded into the wxPanel.

a) I have already circumvented this propagation problem by having a public button-identifier member in my dialog class, which gets set when the user clicks the radio button and that I can then just access from my panel class later. But...

b) Why was this so tricky? I would imagine that quite often we have the situation in which a dialog box asks for user input that then gets dealt with in a parent window. Am I thinking about this program design in the wrong way? For instance, am I already doing it the best way now?

Thanks, all.

Upvotes: 0

Views: 923

Answers (2)

VZ.
VZ.

Reputation: 22688

Event propagation from wxDialog to another, usually completely different, top level window proved to be very confusing and unexpected in practice, so while it did work like this at some time, it was changed a very long time ago. Nowadays, if you really want to get the events from your dialogs in the parent window you need to explicitly clear wxWS_EX_BLOCK_EVENTS style after creating your dialog by using something like

dlg.SetExtraStyle(dlg.GetExtraStyle() & ~wxWS_EX_BLOCK_EVENTS);

Upvotes: 0

ravenspoint
ravenspoint

Reputation: 20457

Have you looked at the sample programs that come with the wxWidgets distribution? They have lots of examples showing you how to do various things

For example, the controls sample has this event table:

BEGIN_EVENT_TABLE(MyPanel, wxPanel)
EVT_IDLE      (                         MyPanel::OnIdle)
EVT_BOOKCTRL_PAGE_CHANGING(ID_BOOK,     MyPanel::OnPageChanging)
EVT_BOOKCTRL_PAGE_CHANGED(ID_BOOK,      MyPanel::OnPageChanged)
EVT_LISTBOX   (ID_LISTBOX,              MyPanel::OnListBox)
EVT_LISTBOX   (ID_LISTBOX_SORTED,       MyPanel::OnListBox)
EVT_LISTBOX_DCLICK(ID_LISTBOX,          MyPanel::OnListBoxDoubleClick)
EVT_BUTTON    (ID_LISTBOX_SEL_NUM,      MyPanel::OnListBoxButtons)
EVT_BUTTON    (ID_LISTBOX_SEL_STR,      MyPanel::OnListBoxButtons)
EVT_BUTTON    (ID_LISTBOX_CLEAR,        MyPanel::OnListBoxButtons)
EVT_BUTTON    (ID_LISTBOX_APPEND,       MyPanel::OnListBoxButtons)
EVT_BUTTON    (ID_LISTBOX_DELETE,       MyPanel::OnListBoxButtons)
EVT_BUTTON    (ID_LISTBOX_FONT,         MyPanel::OnListBoxButtons)

...

This shows that when the user clicks on e.g. the ID_LISTBOX_CLEAR button, the panel method MyPanel::OnListBoxButtons() is invoked.

In general you can invoke any method on any class by specifying the event, the control ID and the method you want to connect together.

"Note that the second argument of macro's (e.g. MyFrame::OnButton1) must always be a member of the class specified in the first argument of BEGIN_EVENT_TABLE." http://wiki.wxwidgets.org/Events#Event_Tables

So, if you want to invoke method M of class C when event E occurs on control D you would write

BEGIN_EVENT_TABLE( C ... )
E ( D C:M )

( BTW using wxWidgets v2.9 with the bind() method is considered preferable to event tables. Since you seem confused about event tables, why not skip learning about them and move directly to v2.9? )

Upvotes: 0

Related Questions