Партнерка на США и Канаду по недвижимости, выплаты в крипто
- 30% recurring commission
- Выплаты в USDT
- Вывод каждую неделю
- Комиссия до 5 лет за каждого referral
public:
CMainWindow();
protected:
afx_msg void OnPaint();
DECLARE_MESSAGE_MAP()
};
#endif
Фрагмент программы 4.1б. Приложение Hello – файл реализации Hello. cpp
#include <afxwin. h> // Описание CWinApp и других классов каркаса приложения MFC
#include "Hello. h"
CMyApp myApp;
// Функции-члены CMyApp
BOOL CMyApp::InitInstance()
{
m_pMainWnd = new CMainWindow;
m_pMainWnd->ShowWindow( m_nCmdShow );
m_pMainWnd->UpdateWindow();
return TRUE;
}
// Карта сообщений и функции-члены CMainWindow
BEGIN_MESSAGE_MAP( CMainWindow, CFrameWnd )
ON_WM_PAINT()
END_MESSAGE_MAP()
CMainWindow::CMainWindow()
{
Create( NULL, "Приложение Hello" );
}
void CMainWindow::OnPaint()
{
CPaintDC dc( this );
CRect rect;
GetClientRect( &rect );
dc. DrawText("Hello, MFC", -1, &rect, DT_SINGLELINE ¦ DT_CENTER ¦ DT_VCENTER );
}
Главное окно приложения Hello показано на рис. 4.1. Это окно является полноценным перекрываемым окном Windows: его можно перемещать, изменять размеры, сворачивать, разворачивать и закрывать. При любом размере окна строка "Hello, MFC" все равно выводится в центре клиентской области.

Рис. 4.1. Главное окно приложения Hello.
2.1 Объект-приложение
Центральная компонента MFC-приложения – объект-приложение подкласса CWinApp. CWinApp содержит цикл обработки сообщений, в котором выполняется выборка и диспетчеризация сообщений в оконную процедуру главного окна приложения. В этом классе есть виртуальные функции, которые можно перегружать для реализации поведения конкретного приложения.
В приложении MFC должен быть ТОЛЬКО ОДИН объект-приложение. Он объявляется в глобальной области видимости, чтобы создание объекта производилось сразу после запуска приложения.
Класс-приложение в программе Hello называется CMyApp. Объект этого класса создается в файле Hello. cpp с помощью оператора описания переменной:
CMyApp myApp;
В классе CMyApp нет переменных членов и есть только одна перегруженная функция, унаследованная от CWinApp – функция-член InitInstance. Она вызывается каркасом сразу после запуска приложения. В InitInstance должно создаваться главное окно приложения. Поэтому даже самое маленькое MFC-приложение должно унаследовать класс от CWinApp и перегрузить в нем функцию InitInstance.
2.2 Функция InitInstance
По умолчанию виртуальная функция CWinApp::InitInstance состоит из единственного оператора возврата:
return TRUE;
InitInstance предназначена для выполнения инициализации, необходимой при каждом запуске программы (как минимум, должно создаваться главное окно приложения). Возвращаемое значение InitInstance является признаком удачной/неудачной инициализации. При неудачной инициализации (значение FALSE) приложение будет завершено.
В CMyApp::InitInstance главное окно приложения является объектом класса CMainWindow, адрес этого объекта сохраняется в переменной-члене CWinApp::m_pMainWnd:
m_pMainWnd = new CMainWindow;
После создания главного окна InitInstance выводит его на экран с помощью функций-членов класса CMainWindow:
m_pMainWnd->ShowWindow( m_nCmdShow ); // Вывод окна на экран
m_pMainWnd->UpdateWindow(); // Обновление содержимого окна
Виртуальные функции ShowWindow и UpdateWindow унаследованы от CWnd – базового класса для всех оконных классов MFC, в том числе и для CFrameWnd, от которого унаследован CMainWindow.
Функция ShowWindow в качестве параметра принимает целочисленный код состояния окна: свернутое, развернутое или обычное (значение по умолчанию SW_SHOWNORMAL). Приложение Hello передает в ShowWindow значение переменной CWinApp::m_nCmdShow, в которой каркас приложения сохраняет параметр nCmdShow функции WinMain.
2.3 Виртуальные функции CWinApp
Кроме InitInstance, в классе CWinApp есть и другие виртуальные функции-члены, которые можно перегружать для выполнения специфических действий приложения. В справочной системе в описании класса CWinApp вы можете увидеть более десяти виртуальных функций, например, WinHelp и ProcessWndProcException, но большинство из низ используются редко.
Функцию ExitInstance можно использовать для освобождения ресурсов при завершении приложения (например, ресурсов и памяти, выделенных в InitInstance). В реализации "по умолчанию" функция ExitInstance выполняет некоторые действия по очистке, предусмотренные в каркасе приложения, поэтому при перегрузке обязательно надо вызывать ExitInstance из базового класса. Значение, возвращенное ExitInstance, является кодом выхода, возвращаемым из WinMain.
Среди других полезных виртуальных функций CWinApp можно назвать OnIdle, Run и PreTranslateMessage. OnIdle удобна для выполнения некоторой фоновой обработки, вроде обновления каких-либо индикаторов. Слово "idle" переводится как "ожидание, простой". Эта функция вызывается. когда очередь сообщений потока пуста. Поэтому OnIdle является удобным механизмом выполнения фоновых задач с низким приоритетом, не требующих отдельного исполняемого потока.
Функцию Run можно перегрузить с целью модификации цикла обработки сообщений, но это делается редко. Если надо выполнить некоторую специфическую предварительную обработку некоторых сообщений до их диспетчеризации, то достаточно перегрузить PreTranslateMessage и не изменять цикл обработки сообщений.
2.4 Порядок использования объекта-приложения каркасом MFC
В исходном тексте приложения Hello заметна характерная особенность MFC-приложений – отсутствие исполняемого кода за пределами классов. В приложении Hello нет ни функции main, ни WinMain. Единственный оператор за пределами классов – это оператор создания объекта-приложения в глобальной области видимости. Чтобы понять, где же в самом деле начинается исполнение программы, надо разобраться в структуре каркаса приложения.
В одном из исходных файлов MFC (они поставляются в комплекте Visual C++), в Winmain. cpp, находится функция AfxWinMain. Она является аналогом WinMain в MFC-приложениях. Из AfxWinMain вызываются функции-члены объекта-приложения – отсюда ясно, почему он должен быть глобальным объектом (глобальные переменные и объекты создаются до исполнения какого-либо кода, а объект-приложение должен быть создан до начала исполнения функции AfxWinMain).
После запуска AfxWinMain для инициализации каркаса приложения вызывает функцию AfxWinInit, которая копирует полученные от Windows значения hInstance, nCmdShow и другие параметры AfxWinMain в переменные-члены объекта-приложения. Затем вызываются функции-члены InitApplication и InitInstance (InitApplication в 32-разрядных приложениях использовать не следует, она нужна для совместимости с Windows 3.x). Если AfxWinInit, InitApplication или InitInstance возвращает FALSE, то AfxWinMain завершает приложение. При условии успешного выполнения всех перечисленных функций AfxWinMain выполняет следующий, крайне важный шаг. У объекта-приложения вызывается функция-член Run и т. о. выполняется вход в цикл обработки сообщений главного окна приложения:
pApp->Run();
Цикл обработки сообщений завершится при получении из очереди сообщения WM_QUIT. Тогда Run вызовет функцию ExitInstance и вернет управление в AfxWinMain. Она выполнит освобождение служебных ресурсов каркаса и затем оператором return завершит работу приложения.
2.5 Класс "окно-рамка" CFrameWnd
В MFC базовым оконным классом является класс CWnd. Этот класс и его потомки предоставляют объектно-ориентированный интерфейс для работы со всеми окнами, создаваемыми приложением. В приложении Hello класс главного окна называется CMainWindow. Он является подклассом CFrameWnd, а тот, в свою очередь, подклассом CWnd. Класс CFrameWnd реализует понятие "окна-рамки". Окна-рамки играют важную роль контейнеров для видов, панелей инструментов, строк состояния и других объектов пользовательского интерфейса в архитектуре "документ/вид". Пока об окне-рамке можно думать как об окне верхнего уровня, которое обеспечивает основной интерфейс приложения с внешним миром.
MFC-приложение для создания окна вызывает его функцию-член Create. Приложение Hello создает объект CMainWindow в функции InitInstance, а в конструкторе CMainWindow как раз и выполняется создание окна Windows, которое потом будет выведено на экран:
Create( NULL, "Приложение Hello" );
Функция-член Create, наследуемая в CMainWindow от CFrameWnd, имеет следующий прототип:
BOOL Create( LPCTSTR lpszClassName,
LPCTSTR lpszWindowName,
DWORD dwStyle = WS_OVERLAPPEDWINDOW,
const RECT& rect = rectDefault,
CWnd* pParentWnd = NULL,
LPCTSTR lpszMenuName = NULL,
DWORD dwExStyle = 0,
CCreateContext* pContext = NULL )
Применение Create упрощается за счет того, что для 6-ти из 8-ми ее параметров определены значения "по умолчанию". Приложение Hello при вызове Create указывает только два первых параметра. Параметр lpszClassName задает имя оконного класса (которое хранится в структуре WNDCLASS), на основе которого операционная система будет создавать новое окно. Если этот параметр задать равным NULL, то будет создано окно-рамка на основе оконного класса, зарегистрированного каркасом приложения. Параметр lpszWindowName задает текст строки заголовка окна.
2.6 Рисование содержимого окна
Приложение Hello выводит текст на экран только по требованию Windows, при обработке сообщения WM_PAINT. Это сообщение генерируется по разным причинам, например, при перекрытии окон или при изменении размеров окна. В любом случае, само приложение ответственно за перерисовку клиентской области окна в ответ на WM_PAINT.
В приложении Hello сообщения WM_PAINT обрабатываются функцией CMainWindow::OnPaint, которая вызывается каркасом приложения при получении каждого сообщения WM_PAINT. Эта функция выводит строку "Hello, MFC" в центре клиентской области окна. Функция начинается с создания объекта класса CPaintDC:
|
Из за большого объема этот материал размещен на нескольких страницах:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |


