第 3 章 初学wxWidgets

目录

第一个程序
事件驱动(Event-Driven)
让一个事件可以被多次处理
在窗体中加载/移出事件表
自定义事件表
动态事件表
自定义事件
细节
事件标示符
窗体风格
自定义事件类和事件宏
常用名词解释

第一个程序

首先说明一下:本教程比较侧重于代码的实践,最好接合"Cross-Platform GUI Programming with wxWidgets"来读(网上有电子书,自己搜索一下),不过我写的还是自认为写的比较详细,单独阅读问题也应该不是很大.wxWidgets用户手册是必备的,伟大的孙波同志正在翻译中文版 ,希望他可以坚持到底!大家可以在邮件列表中找到不完全翻译版,名字叫"wxWidgets 2.6.1: 一个可移植的C++和Python图形用户接口工具包(GUI toolkit)".

另外请高手们多多指教,更期待有志同道合者可以一起来完成这个教程.ok,我们开始吧!

wxWidgets库的,是一个结构类似于MFC的开源的C++库,它的特点是跨平台:一次编程便可以在从XP到Linux,苹果机,WinCE等等操作系统上重新编译,运行.

安装和编译wxWidgets库我就不说了,大家可以参考Code Project上的"Introduction to wxWidgets"(作者:Priyank Bolia,期待哪位英文好的高手翻译一下)(我放在附件中了).

[小心]注意:"Introduction to wxWidgets"中路径设置的问题

环境变量"WXWIN"应该设置为"c:\???"而不是"c:\???\",然后包含目录的时候格式为"$(WXWIN)\include\"而不是"$(WXWIN)include\".我也提供了一个VS2003修正版的"HelloWorld"的解决方案(本文的源代码只需直接复制到hello.cpp中便可编译运行).

照着这篇文章安装,编译,设置环境变量之后,就可以开始我们的程序了.我的IDE是VS2003(Microsoft Visual Studio .NET 2003),wxWidgets库的版本是2.6.1.

图 3.1. 第一个程序的截图

第一个程序的截图

先了解一下"HelloWorld"的源代码

过程 3.1. 程序的调用顺序

  1. 用宏绑定main函数

  2. MyApp::OnInit()

    1. MyFrame初始化:设置界面布局,绑定按钮到事件表

    2. 通知计算机显示MyFrame

  3. 被按下按钮-->回调事件表中的相应函数

#include "wx/wx.h" 
#include "mainico.xpm"//包含图标文件,格式为XPM,我在源代码之后有该格式的说明

//新建一个窗体
class MyFrame: public wxFrame
{
public:

	MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size);

	//事件处理函数
	void OnQuit(wxCommandEvent& event);
	void OnAbout(wxCommandEvent& event);

	//这个呢,写过MFC的朋友一定眼熟,就是消息映射了,wxWidgets叫事件表
	DECLARE_EVENT_TABLE()
};

enum
{
	ID_Quit,
	ID_About,
};

//这里是事件的映射,当触发什么事件(如MENU_ABOUT)时候,调用什么函数(MyApp::OnAbout)
BEGIN_EVENT_TABLE(MyFrame, wxFrame)
EVT_MENU(ID_Quit, MyFrame::OnQuit)
EVT_MENU(ID_About, MyFrame::OnAbout)
END_EVENT_TABLE()

//初始化程序
class MyApp: public wxApp
{
	virtual bool OnInit();
};

//把main函数放在这里
IMPLEMENT_APP(MyApp)

//程序初始化的代码
bool MyApp::OnInit()
{
	/*
	wxT("Hello World")中"wxT"是一个宏,也可以写作"_T()",用于在编译时改变文字的编码.
	比如,一个程序可以分别编译为ASCLL码版(只支持英文)和UTF-8版(支持多国语言)
	*/
	MyFrame *frame = new MyFrame( wxT("Hello World"), wxPoint(299,250), wxSize(340,340) );
	frame->Show(TRUE);
	SetTopWindow(frame);
	return TRUE;
} 

MyFrame::MyFrame(const wxString& title, const wxPoint& pos, const wxSize& size)
: wxFrame((wxFrame *)NULL, -1, title, pos, size)	
//wxFrame中的初始化参赛以及其含义可以参见Gxl117翻译的《wxWindows 2用C++编写跨平台程序》(本文的附件中有)
{
	SetIcon(wxIcon(mainico_xpm));//设置图标(mainico_xpm变量在mainico.xpm被声明)

	wxMenu *menuFile = new wxMenu;//菜单条中一个条目

	menuFile->Append( ID_About, wxT("&A菜单项--弹出窗口") );
	menuFile->AppendSeparator();
	menuFile->Append( ID_Quit, wxT("&Q退出") );

	wxMenuBar *menuBar = new wxMenuBar;//菜单条
	menuBar->Append( menuFile, wxT("&M菜单条中的条目" ));

	SetMenuBar( menuBar );

	CreateStatusBar();
	SetStatusText(wxT( "欢迎使用wxWidgets!") );//状态栏
}

void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event))
{
	Close(TRUE);
}

void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
{
	wxMessageBox(wxT("消息框的文字:地球人,你好!"),
		wxT("消息框的标题"),
		wxOK | wxICON_MASK ,
		this);
}

[提示]XPM图像格式说明

把其他图片格式转换为XPM格式可以用一个免费软件XnView(有汉化版),另外图片该程序的图标大小应该为16*16像素。 用文本编辑器打开XPM文件后可以看到内容如下:

/* XPM */
static char *mainico_xpm[] = {
/* width height num_colors chars_per_pixel */
"    16    16      256            2",
/* colors */
"`` c #000000",
"`. c #173b03",
"`# c #62ce19",
...................等等