How "wxStdDialogButtonSizer" works Topic is solved

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
Bathes
In need of some credit
In need of some credit
Posts: 2
Joined: Fri Nov 20, 2020 6:08 pm

How "wxStdDialogButtonSizer" works

Post by Bathes »

Hi, I'm trying to use "wxStdDialogButtonSizer", but It don't work like I expected. I use Code::Block with wxSmith to edit my GUI and I have added Save/Cancel buttons to my dialog. Only the Cancel button does something (close the dialog). "Save" button doesn't do anything.

I have try to add button by code instead of by wxSmith, But I don't think is the way to do it.
The following code work, but I don't see the buttons created in the wxSmith editor. I want to use the integreated buttons in the "wxStdDialogButtonSizer" to be able to see the look in wxSmith editor.

Code: Select all

ButSave = new wxButton(this, Id_ButSave, _("Save"), wxDefaultPosition, wxDefaultSize, 0, wxDefaultValidator, _T("Id_ButSave"));
StdDialogButtonSizer->AddButton(ButSave);
ONEEYEMAN
Part Of The Furniture
Part Of The Furniture
Posts: 7459
Joined: Sat Apr 16, 2005 7:22 am
Location: USA, Ukraine

Re: How "wxStdDialogButtonSizer" works

Post by ONEEYEMAN »

Hi,
You need to write a handler for a button click.

Thank you.
Bathes
In need of some credit
In need of some credit
Posts: 2
Joined: Fri Nov 20, 2020 6:08 pm

Re: How "wxStdDialogButtonSizer" works

Post by Bathes »

I was trying to create a button in "wxStdDialogButtonSizer" but you just need to create a handler for the button that is created with the "wxStdDialogButtonSizer". Like "ONEEYEMAN" said. By using the right "wxID". To maybe help someone else I have write all steps.

Just create "command event function" in ".h" file and implement it in ".cpp" file. After that we need to connect, in the constructor, the "button's id" with the "command event function" created earlier.

It will look like that:
headers file:

Code: Select all

class myWxDialog: public wxDialog{
	public:
		myWxDialog(/*param*/);
		virtual ~myWxDialog();
		//Some Stuff
	protected:
		//Some Stuff
	private:
		//Some Stuff
		void OnButSaveClick(wxCommandEvent& event);
		void OnButCancelClick(wxCommandEvent& event);

		DECLARE_EVENT_TABLE()
};
cpp file:

Code: Select all

myWxDialog::myWxDialog(/*param*/){
	//(*Initialize(ConfigurationDialog) //Auto generated code
	//Some stuff
	StdDialogButtonSizer = new wxStdDialogButtonSizer();
	StdDialogButtonSizer->AddButton(new wxButton(this, wxID_CANCEL, wxEmptyString)); // the id for the cancel button is: wxID_CANCEL
	StdDialogButtonSizer->AddButton(new wxButton(this, wxID_SAVE, wxEmptyString)); // the id for the save button is: wxID_SAVE
	StdDialogButtonSizer->Realize();
	//Some stuff
	//*) //End - Auto generated code
	
	//Connect button in "StdDialogButtonSizer"
	Connect(wxID_SAVE,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&myWxDialog::OnButSaveClick);
	Connect(wxID_CANCEL,wxEVT_COMMAND_BUTTON_CLICKED,(wxObjectEventFunction)&myWxDialog::OnButCancelClick);
}

void myWxDialog::OnButSaveClick(wxCommandEvent& event){
    // Save stuff
	wxMessageBox("You have click on save button. myWxDialog::OnButSaveClick");
    this->Close();
}

void myWxDialog::OnButCancelClick(wxCommandEvent& event){
	wxMessageBox("myWxDialog::OnButCancelClick");
    this->EndModal(0);
}
rando
Knows some wx things
Knows some wx things
Posts: 35
Joined: Fri Nov 09, 2018 9:11 pm

Re: How "wxStdDialogButtonSizer" works

Post by rando »

I modified your code, the below should work. It uses Bind() instead of Connect()
https://docs.wxwidgets.org/3.0/overview_events.html

wxFAIL_MSG() will show a message box if in debug mode, does nothing in release. If you click Stop it will break into your code at the wxFAIL_MSG else continues execution

If opening a dialog with ShowModal() then you must call EndModal() to close it.

Code: Select all

Header File
// ... other includes
#include <wx/debug.h>
class myWxDialog: public wxDialog{
	public:
		myWxDialog(/*param*/);
		virtual ~myWxDialog();
		//Some Stuff
	protected:
		//Some Stuff
	private:
		//Some Stuff
		void OnButtonClick(wxCommandEvent& event);
		// Pass the event to the handler if necessary, return false to prevent dialog closure
		bool HandleButtonSave(/*wxCommandEvent& event*/);
		bool HandleButtonCancel(/*wxCommandEvent& event*/);
};

Code: Select all

CPP File
myWxDialog::myWxDialog(/*param*/){
	//(*Initialize(ConfigurationDialog) //Auto generated code
	//Some stuff
	StdDialogButtonSizer = new wxStdDialogButtonSizer();
	StdDialogButtonSizer->AddButton(new wxButton(this, wxID_CANCEL)); // the id for the cancel button is: wxID_CANCEL
	StdDialogButtonSizer->AddButton(new wxButton(this, wxID_SAVE)); // the id for the save button is: wxID_SAVE
	StdDialogButtonSizer->Realize();
	//Some stuff
	//*) //End - Auto generated code
	// Use Bind() and then you do not need event tables and can dynamically bind/unbind events which is very useful
	Bind(wxEVT_BUTTON, &myWxDialog::OnButtonClick, this);
}

// In this case, the Unbind() is not necessary, I include for completeness of the example
myWxDialog::~myWxDialog()
{
	// Exactly the same arguments as the Bind() call
	Unind(wxEVT_BUTTON, &myWxDialog::OnButtonClick, this);
}

void OnButtonClick( wxCommandEvent& event)
{
	// The dialog will handle the button click return value, we just need to do local stuff then event.Skip()
	auto do_close{false};
	switch( event.GetId() )
	{
		case wxID_SAVE:
			do_close = HandleButtonSave();
			break;
		case wxID_CANCEL:
			do_close = HandleButtonCancel();
			break;
		default: wxFAIL_MSG("Unhandled event Id");
	}
	// All button clicks lead to dialog closure on success, EndModal() here will return the wxID from this event to the
	// caller of ShowModal()
	if( do_close )
	{
		EndModal();
	}
	event.Skip(); // Pass to next handler in the chain
}

bool myWxDialog::HandleButtonSave(/*wxCommandEvent& event*/){
	auto stuff_saved{false};
    // Save stuff, and set stuff_saved true on success
	if( stuff_saved)
	{
		// Show success message
	}
	else
	{
		// Show fail message
	}
	return stuff_saved;
}

bool myWxDialog::OnButCancelClick(wxCommandEvent& event){
	return ( wxMessageBox("Close this dialog?", "Confirm", wxYES_NO, this) == wxYES);
}
Post Reply