1. GUI用户界面元素
(1)操作系统提供了创建用户界面元素所需要的函数
(2)各种功能不同的函数依次调用,从而创建出界面元素
(3)操作系统提供的原生函数无法直接映射到界面元素
2. 面向对象的GUI程序设计
(1)GUI应用程序是为了解决非科学计算问题而诞生的
(2)GUI应用程序适用于非专业的日常生活领域
(3)面向过程程序设计方法学不适合GUI程序设计
(4)面向对象程序设计方法学更适合GUI程序设计
3. 另一种眼界
(1)用面向对象方法学看待GUI界面元素
(2)所有界面元素都可以看作实际的对象
(3)GUI用户界面是由各不相同的对象组成的(如菜单对象、按钮对象、文本框对象等)
(4)用面向对象的思想开发GUI应用程序(界面元素对应哪些类?)
①将界面元素定义为对应的类
②通过抽象和封装可以隐藏界面元素的细节
③程序的创建过程就是组合不同界面元素对象的过程
【实例分析】面向对象的方法创建GUI程序
//Main.cpp
#include <windows.h> #include "Application.h" #include "MainWindow.h" #include "PushButton.h" BOOL WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { Application a(hInstance, lpCmdLine); MainWindow w(hInstance, L"Main Window"); PushButton b(&w, L"My Button"); w.show(); return a.exec(); }
//Application.h
#pragma once #include <windows.h> class Application { public: Application(HINSTANCE hInstance, LPSTR lpCmdLine); bool exec(); };
//Application.cpp
#include "Application.h" Application::Application(HINSTANCE hInstance, LPSTR lpCmdLine) { } bool Application::exec() { MSG msg = { 0 }; //进入消息循环 while ( GetMessage(&msg, NULL, 0, 0)) { //翻译并转换系统消息 TranslateMessage(&msg); //分发消息到对应的消息处理函数 DispatchMessage(&msg); } return TRUE; }
//Widget.h
#pragma once #include <windows.h> class Widget { protected: Widget* m_parent; HWND m_hwnd; public: Widget(); Widget(Widget* parent); HWND hwnd(); Widget* parent(); };
//Widget.cpp
#include "Widget.h" Widget::Widget() { m_parent = NULL; } Widget::Widget(Widget* parent) { m_parent = parent; } HWND Widget::hwnd() { return m_hwnd; } Widget* Widget::parent() { return m_parent; }
//MainWidow.h
#pragma once #include "Widget.h" class MainWindow : public Widget { protected: static const wchar_t STYLE_NAME[]; //主窗口定义 BOOL DefineMainWindow(HINSTANCE hInstance); //主窗口创建 void CreateMainWindow(HINSTANCE hInstance, const wchar_t* title); //主窗口消息处理函数 static LRESULT CALLBACK WndProc(HWND hWnd, int message, WPARAM wParam, LPARAM lParam); public: MainWindow(HINSTANCE hInstance, const wchar_t* title); void show(); };
//MainWindow.cpp
#include "MainWindow.h" const wchar_t MainWindow::STYLE_NAME[] = L"MainForm"; //主窗口定义 BOOL MainWindow::DefineMainWindow(HINSTANCE hInstance) { static WNDCLASS WndClass = { 0 };//系统结构类型,用于描述窗口样式 WndClass.style = 0; WndClass.cbClsExtra = 0; WndClass.cbWndExtra = 0; WndClass.hbrBackground = (HBRUSH)(COLOR_WINDOW); //定义窗口背景色 WndClass.hCursor = LoadCursor(NULL, IDC_ARROW); //定义鼠标样式 WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION); //定义窗口左上角图标 WndClass.hInstance = hInstance; //定义窗口样式属于当前应用程序 WndClass.lpfnWndProc = (WNDPROC)WndProc; //窗口消息处理函数 WndClass.lpszClassName = STYLE_NAME; //窗口样式名 WndClass.lpszMenuName = NULL; //将定义好的窗口样式注册到系统上 return RegisterClass(&WndClass); } //主窗口创建 void MainWindow::CreateMainWindow(HINSTANCE hInstance, const wchar_t* title) { m_hwnd = CreateWindow(STYLE_NAME, //通过定义好的窗口样式创建主窗口 title, //主窗口标题 WS_OVERLAPPEDWINDOW,//创建后主窗口的显示风格 CW_USEDEFAULT, //主窗口左上角x坐标 CW_USEDEFAULT, //主窗口左上角y坐标 CW_USEDEFAULT, //主窗口宽度 CW_USEDEFAULT, //主窗口高度 NULL, //父窗口 NULL, //主窗口菜单 hInstance, //主窗口属于当前应用程序 NULL); } //主窗口消息处理函数 LRESULT CALLBACK MainWindow::WndProc(HWND hWnd, int message, WPARAM wParam, LPARAM lParam) { switch (message) { case WM_DESTROY: PostQuitMessage(0); break; default: //调用系统提供的默认消息处理函数 return DefWindowProc(hWnd, message, wParam, lParam); } return 0; } MainWindow::MainWindow(HINSTANCE hInstance, const wchar_t* title) :Widget(NULL) { DefineMainWindow(hInstance); CreateMainWindow(hInstance, title); } void MainWindow::show() { ShowWindow(m_hwnd, SW_SHOWNORMAL); //显示窗口 UpdateWindow(m_hwnd); //刷新窗口 }
//PushButton.h
#pragma once #include "Widget.h" class PushButton : public Widget { public: PushButton(Widget* win, const wchar_t* text); };
//Pushbutton.cpp
#include "PushButton.h" PushButton::PushButton(Widget* win, const wchar_t* text) { HINSTANCE hInstance = (HINSTANCE)GetWindowLong(win->hwnd(), GWL_HINSTANCE); m_hwnd = CreateWindow(L"button", //通过系统预定义的窗口样式创建元素 text, //窗口元素标题 WS_CHILD | WS_VISIBLE | BS_PUSHBUTTON,//创建后窗口元素的显示风格 50, //窗口元素在主窗口左上角x坐标 50, //窗口元素在主窗口左上角y坐标 200, //窗口元素宽度 60, //窗口元素高度 win->hwnd(), //父窗口 (HMENU)this, //窗口元素ID值 hInstance, //窗口元素属于当前应用程序 NULL); }
4. QT的本质
(1)QT是利用面向对象方法学开发的一套GUI组件库
(2)QT将不同操作系统的GUI细节封装于类的内部
(3)QT提供一套跨平台的类,用于开发GUI程序
(4)QT遵循经典的GUI应用程序开发模式
5. 小结
(1)GUI程序开发更适合采用面向对象方法学
(2)所有的界面元素都可以看作实际的对象
(3)GUI用户界面是由各不相同的对象组成的
(4)QT是利用面向对象方法学开发的一套GUI组件库
(5)QT将GUI细节封装于类的内部,具有跨平台的特性