problem in event handler

If you are using the main C++ distribution of wxWidgets, Feel free to ask any question related to wxWidgets development here. This means questions regarding to C++ and wxWidgets, not compile problems.
Post Reply
Qasim
Knows some wx things
Knows some wx things
Posts: 29
Joined: Wed May 23, 2007 3:41 pm
Location: London

problem in event handler

Post by Qasim » Tue May 13, 2008 6:42 pm

Hi. I am trying to use static event handler for my control but not getting any where(dynamic works fine though). This is how I am doing it

Code: Select all

class MyClass : public wxEvtHandler
{
public:
...
enum {ID_RB0, ID_RB1};
MyClass(wxWindow* parent)
void CreateControl();
void OnRB0(wxCommandEvent&);
void OnRB1(wxCommandEvent&);
...
DECLARE_EVENT_TABLE()
};
in cpp file

Code: Select all

BEGIN_EVENT_TABLE(MyClass, wxEvtHandler)
EVT_RADIOBUTTON(ID_RB0, MyClass::OnRB0)
EVT_RADIOBUTTON(ID_RB1, MyClass::OnRB1)
END_EVENT_TABLE()


void CreateControl()
{
wxRadioButton *rb0 = new wxRadioButton(parent, ID_RB0,...);
}
void MyClass::OnRB0(wxCommandEvent& e)
{
}
//same goes for OnRB1
But this never breaks into OnRB0 & OnRB1 unless using Connect(...). Then I tried to make it work by deriving directly from wxFrame, which works perfectly fine, but not what I require. So I must be doing some thing wrong here. Any help will be appreciated.
Who doubts nothing, Knows nothing

DavidHart
Site Admin
Site Admin
Posts: 4051
Joined: Thu Jan 12, 2006 6:23 pm
Location: IoW, UK

Post by DavidHart » Tue May 13, 2008 7:04 pm

Hi,

Unless you've missed out those bits of code, it looks as if CreateControl() isn't a member of MyClass, and MyClass isn't the parent of the radiobuttons. That means you can't catch the radiobutton events in the MyClass event table.

A control's events go first to that control; then (for command events) if not already handled, or if Skip()ed, the event is passed to the control's parent, then the grandparent etc. MyClass isn't in that hierarchy, so it won't see the events.

One of the few advantages of using Connect() is that events can be passed sideways, to whichever wxEvtHandler-derived class you like. That's why it works here, while the static event table doesn't.

Regards,

David

blitzkriegten
Earned a small fee
Earned a small fee
Posts: 20
Joined: Wed Mar 28, 2007 5:55 pm
Location: Baltimore, MD
Contact:

What is the advantage of Connect() method ?

Post by blitzkriegten » Wed May 14, 2008 6:54 pm

Hi All,

I am wondering about he advantage of using Connect() method ? If anyone having any idea, please let me know.

Regards
CG

Greg Domjan
In need of some credit
In need of some credit
Posts: 4
Joined: Wed May 14, 2008 3:51 am

Post by Greg Domjan » Thu May 15, 2008 1:21 am

Blitzkriegten,

The advantage of using Connect() is that you can dynamically create interface components and still have message handling with specific linkage to components.

ie.

Code: Select all

wxbutton *a = new wxbutton( this, _("Dynamic"));
this->GetEventHandler()->Connect( a->GetId(), wxEVT_COMMAND_BUTTON_CLICKED, ... );

wendahan
In need of some credit
In need of some credit
Posts: 1
Joined: Thu May 15, 2008 4:38 am

Post by wendahan » Thu May 15, 2008 4:44 am

you should call parent->PushEventHandler first

MyClass::MyClass(...){
parent->PushEventHandler(this);
}

MyClass::~MyClass(...){
parent->PopEventHandler();
}

DavidHart
Site Admin
Site Admin
Posts: 4051
Joined: Thu Jan 12, 2006 6:23 pm
Location: IoW, UK

Re: What is the advantage of Connect() method ?

Post by DavidHart » Thu May 15, 2008 10:37 am

blitzkriegten wrote:Hi All,

I am wondering about he advantage of using Connect() method ? If anyone having any idea, please let me know.
I know of three advantages:
  • As mentioned above, Connect() lets you handle events outside the originating class hierarchy.

    It's dynamic, so it's useful when you want to deal with a variable number of controls e.g. the user adding buttons to a toolbar. There are ways of doing this with event tables (EVT_MENU_RANGE, or wxID_ANY) but Connect() is a more elegant solution.

    You can Disconnect() when you don't want to receive more events. I use this when I only want to do something once, e.g. when a newly-created control has achieved its proper size: Connect() idle events on creation, check with GetSize() in the handler, do what's needed if the size is genuine, then Disconnect().
The main drawback is that it's so much easier to get Connect() wrong, usually because of an incorrect eventSink parameter. Search this forum, and you'll see lots of pleas for help with Connect(), but far fewer for event tables.


wendahan: PushEventHandler should work too. I've not used it in this way. but iiuc that means that all MyClass events, of all types, will go first to 'parent'. This will usually not be what is wanted, and there is obvious scope for error and confusion.

Regards,

David

Post Reply