A GUI toolkit is a set of header files and libraries that makes GUI development easier for developers. There are several GUI toolkits available in the market, few of them are stated as follows:
We'll focus on wxWidgets toolkit in this book due to its simpler licensing model, native look and feel, and cross-platform development capability. A compiled copy of wxWidgets is also provided with the book. This book assumes that reader has extracted compiled wxWidgets to Z:wxWidgets
folder.
In order to understand similarities between Win32 API and wxWidgets we will recreate App9
functionalities with wxWidgets.
App11
as the Project title and click on the Next button. Click on the Next button to skip Project details page.$(#wx
) is a global variable, which is pointing to wxWidgets installation directory. Alternatively full path to wxWidgets that is Z:wxWidgets
in our case may be entered here:App11Main.h
file with the following code:#ifndef APP11MAIN_H #define APP11MAIN_H #include <wx/wx.h> #include <wx/sizer.h> #include <wx/button.h> class App11Frame: public wxFrame { public: App11Frame(wxFrame *frame, const wxString& title); ~App11Frame(); private: static const long idBtnClickMe; wxBoxSizer* m_boxSizerMain; wxButton* m_btnClickMe; void OnClickMe(wxCommandEvent& event); void OnClose(wxCloseEvent& event); DECLARE_EVENT_TABLE() };
An App11Frame
class has been derived from a wxFrame
class. A wxFrame
class represents a basic window. Member variable m_btnClickMe
has been defined to create and store button and idBtnClick
will store it's ID for event processing. We have placed a DECLARE_EVENT_TABLE()
function macro to create boiler plate code for event handling related to this class.
App11Main.cpp
file with the following code:#include "App11Main.h" const long App11Frame::idBtnClickMe = ::wxNewId(); BEGIN_EVENT_TABLE(App11Frame, wxFrame) EVT_BUTTON(idBtnClickMe, App11Frame::OnClickMe) EVT_CLOSE(App11Frame::OnClose) END_EVENT_TABLE() App11Frame::App11Frame(wxFrame *frame, const wxString& title) : wxFrame(frame, -1, title) { this->SetSizeHints(wxDefaultSize, wxDefaultSize); m_boxSizerMain = new wxBoxSizer(wxHORIZONTAL); m_btnClickMe = new wxButton(this, idBtnClickMe, _T("Click Me!"), wxDefaultPosition, wxDefaultSize, 0); m_boxSizerMain->Add(m_btnClickMe, 0, wxALL, 5); this->SetSizer(m_boxSizerMain); this->Layout(); } App11Frame::~App11Frame() { } void App11Frame::OnClose(wxCloseEvent &event) { Destroy(); } void App11Frame::OnClickMe(wxCommandEvent& event) { wxMessageBox(_T("Hello World!"), _T("Information"), wxOK | wxICON_INFORMATION, this); }
An event table has been laid out using BEGIN_EVENT_TABLE()
and END_EVENT_TABLE()
macros. This defines relationship of callback functions with respective events. The OnClickMe()
function has been connected to button press event. It will show a message whenever the Click Me! button is pressed by the user.
The OnClose()
function will be called when app closed. It calls a Destroy()
function that initiates app shutdown.
App11App.h
file with the following code:#ifndef APP11APP_H #define APP11APP_H #include <wx/app.h> class App11App : public wxApp { public: virtual bool OnInit(); }; #endif // APP11APP_H
In the preceding file we have derived a class App11App
from wxApp
. A virtual function OnInit()
is implemented in this class.
App11App.cpp
file:#include "App11App.h" #include "App11Main.h" IMPLEMENT_APP(App11App); bool App11App::OnInit() { App11Frame* frame = new App11Frame(0L, _("wxWidgets Application Template")); #ifdef __WXMSW__ frame->SetIcon(wxICON(aaaa)); // To Set App Icon #endif frame->Show(); return true; }
In the implementation of OnInit()
function an object named frame
has been derived from the App11Frame
class. Resource files are available only on Windows platform. Thus it has been enclosed within a pre-processor macro __WXMSW__
and subsequently app is launched in line number 12
.
resource.rc
file as it is.Earlier we mentioned about cross-platform development capability of wxWidgets. Let's put that capability into action. We'll compile App11
source without any change on Linux platform. For this example, we are using CentOS 6 Linux.
In order to compile on Linux platform, we'll use a Makefile
. Remember we can also use the Code::Blocks wxWidgets project wizard to generate a project targeted at Linux platform. However in my opinion developers should be familiar with the Make
tool.
Make is a build tool that can be used any number of source files to a binary based files on a set of rules inside a text file known as a Makefile
. Make handles build dependencies efficiently and for a large project make will only compile relevant files, which has changed since last build. This saves time and also eliminates any human error in the entire build process.
Perform the following steps:
Makefile
:CPP=g++ CXXFLAGS=-c $(shell wx-config --cflags) LDFLAGS=$(shell wx-config --libs) SOURCES=App11Main.cpp App11App.cpp App11: App11Main.o App11App.o $(CPP) $(LDFLAGS) App11Main.o App11App.o -o App11 App11Main.o: $(CPP) $(CXXFLAGS) App11Main.cpp App11App.o: $(CPP) $(CXXFLAGS) App11App.cpp clean: rm -rf *.o App11
In this file several variables are defined in first four lines. The CPP
variable defines C++ compiler binary, CXXFLAGS
stores necessary compiler flags for a wxWidgets
project by running a script wx-config
. The wxWidgets project provides a shell script known as wx-config
that can be used determine compiler and linker flags.
LDFLAGS
stores necessary linker flags used for executable binary generation. SOURCES
variable define the sources that are to be compiled. Do note that we are not using resource.rc
file anymore as resource compiler doesn't exist on Linux platform.
App11:
line defines a make target App11
which comprises two sub-targets App11Main.o
and App11App.o
. There is a shell command defined in the following line which indicates the command to be executed after all sub-targets are built successfully. Subsequently both these targets are also defined in a similar manner.
clean: target executes a command to delete all object files and our executable binary.
[biplab@centos App11]$ make
[biplab@centos App11]$ ./App11
We find that our app now runs on Linux platform flawlessly. It behaves exactly as we wanted it to. We didn't make any changes to the code we wrote for Windows platform. But our GUI toolkit has internally mapped our code to appropriate functions for Linux platform. This gives an immense advantage to a developer as targeting multiple platforms becomes a lot easier.
3.139.97.40