Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
TPKS.docx
Скачиваний:
11
Добавлен:
16.03.2016
Размер:
51.33 Кб
Скачать

3. Організація простої mfc-програми (класи, функції). Послідовність роботи програми.

В простейшем случае программа, написанная с помощью MFC, содержит два класса, порождаемые от классов иерархии библиотеки: класс, предназначенный для создания приложения, и класс, предназначенный для создания окна. Другими словами, для создания минимальной программы необходимо породить один класс от CWinApp, а другой - от CFrameWnd. Эти два класса обязательны для любой программы.

simpwin.hpp

#include <afxwin.h> // Класс основного окна приложения

class CMainWin: public CFrameWnd {

public:

CMainWin(); // Декларирование карты сообщений

DECLARE_MESSAGE_MAP()

}; // Класс приложения. Должен существовать только один экземпляр этого класса. Член-функция InitInstance() вызывается при запуске приложения.

class CApp: public CWinApp {

public:

BOOL InitInstance();

};

simpwin.cpp

#include <afxwin.h>

#include <string.h>

#include "SIMPWIN.HPP" // Создание одного и только одного экземпляра приложения

CApp App;

// Реализация

BOOL CApp::InitInstance()

{ // Создание главного окна приложения и его отображение.Член CApp::m_pMainWnd - это указатель на объект главного окна. m_pMainWnd = new CMainWin;

m_pMainWnd->ShowWindow(SW_RESTORE);

m_pMainWnd->UpdateWindow();

// Сигнализируем MFC об успешной инициализации

// приложения.

return TRUE;

}

CMainWin::CMainWin()

{

// Создание окна с заголовком. Используется

// встроенный в MFC

// класс окна, поэтому первый параметр 0.

this->Create(0, "Простейшее приложение на MFC");

}

// Реализация карты сообщений

BEGIN_MESSAGE_MAP(CMainWin /*класс окна*/, CFrameWnd

/*класс-предок*/)

END_MESSAGE_MAP()

4. Організація обробки повідомлень. Приклади обробки повідомлень.

В MFC включен набор предопределенных функций-обработчиков сообщений, которые можно использовать в программе. Если программа содержит такую функцию, то она будет вызываться всякий раз, когда поступает связанное с ней сообщение. При наличии дополнительной информации в сообщении она передается в качестве аргументов функции. Для организации обработки сообщений нужно выполнить следующие действия: В карту сообщений программы должна быть включена команда соответствующего сообщения. Прототип функции-обработчика должен быть включен в описание класса, ответственного за обработку данного сообщения. В программу должна быть включена реализация функции-обработчика.

КОНСПЕКТ: Обработка сообщений MFC программ. При помощи обработки сообщений определяется реакция программы на действие пользователя, на системные события и на события других программ. WM_MOVE - окно сдвинуто. WM_CLOSE - должно быть закрыто. WM_SIZE - сообщение об изменении размера окна. WM_COMMAND - выбран элемент WM_TIMER WM_MOUSEMOVE WM_LBUTTONDOWN WM_MOUSEWHELL. Для обработки сообщений в MFC-программе создается карта сообщений. А в более ранних версиях - при помощь оператора switch. Для обработки сообщений в классе окна объявляется карта сообщений: class CMainWin: public CFrameWnd {public: CMainWin(); DECLARE_MESSAGE_MAP()}; //App.cpp BEGIN_MESSGE_MAP (CMainWin (класс владельца КС), CFrameWnd (родитель владельца)) Для обработки сообщений в карту сообщений записываются макрокоманды

5. Обробка повідомлень WM_CHAR, WM_PAINT.

WM_CHAR - нажата кнопка на клавиатуре. WM_PAINT - необходимо обновление окна.

Пример обработчика нажатия клавиш клавиатуры

char str [80]; // строка символов для вывода

void CMainWin::OnChar(UINT nChar, UINT nRepCnt, UINT nFlags)

{CClientDC dc(this); // получение контекста окна

dc.TextOut(1,1," ", 3); // удаление старого текста

wsprintf(str,"%с", ch); // формирование строки с кодом клавиши

dc.TextOut(1, 1, str, strlen(str)); } // вывод строки в координату (1, 1)

Таким образом, каждый раз, когда необходимо вывести информацию в рабочую область окна, необходимо получить контекст устройства с помощью CClientDC. Частным случаем является применения сообщения WM_PAINT.

Для обновления содержимого рабочего окна программы необходимо отослать сообщение WM_PAINT. Вне его применения содержимое окна может не отображаться. Т.е. каждый раз, когда есть потребность выводить информацию в окно программы, следует обращаться к этому сообщению.

Сообщению WM_PAINT отвечает макрокоманда ON_WM_PAINT(), а макрокоманде – обработчик OnPaint(). Этот обработчик может выглядеть следующим образом:

Пример обработчика сообщения WM_PAINT

void CMainWin::OnPaint()

{CPaintDC dc(this); // получение контекста окна

dc.TextOut(1,1, str, strlen(str));} // отображение символа

В примере приведен обработчик OnPaint(), который обеспечивает вывод на экран символа, введенного с клавиатуры пользователем соответственно обработчику OnChar(), записанному в предыдущем примере. Видно, что для получения контекста устройства здесь использован объект другого типа, а именно CPaintDC. В отличие от CClientDC, который работает только с клиентской частью окна программы, CPaintDC обеспечивает роботу со всей плоскостью окна.

В программе желательным было бы, чтобы Windows самостоятельно решала, когда ей вызвать сообщение WM_PAINT. Это так и происходит, например, когда пользователь программы минимизирует окно, максимизирует, движет экраном, изменяет размеры окна и т.п.. Но иногда необходимо проводить обновление окна принудительно. Для того, чтобы прислать сообщение WM_PAINT, программа вызывает функцию InvalidateRect() – член класса CWnd, которая имеет следующий прототип:

void CWnd::InvalidateRect(LPCRECT lpRegion, BOOL Erase=TRUE);

где lpRegion – указатель на область окна, которую необходимо обновить, Erase – флаг, который в значении TRUE устанавливает изъятие предыдущего содержимого окна. Если указать первому параметру значения NULL, произойдет полное обновление окна. Вызов функции InvalidateRect() обеспечивает принудительную посылку сообщения WM_PAINT и выполнение обработчика OnPaint().

Полное обновление окна, как например:

InvalidateRect(NULL);

занимает много ресурсов системы, которая визуально может выглядеть мерцанием рабочего окна программы. Этого можно избегнуть, задав отдельно область обновления, например:

СRect region(10,10,100,100);

InvalidateRect(region);

в таком случае будет обновляться лишь область, ограниченная прямоугольником с левым верхним углом (10,10) и нижним правым углом (100,100). Такой вариант обновления становится особенно интересным, если необходимо обеспечить подвижность отдельных элементов окна, а этого можно достичь с одновременным применением обработки сообщения таймера WM_TIMER.

6. Обробка повідомлень WM_LBUTTONDOWN, WM_RBUTTONDOWN.

Рассмотрим программу, которая реагирует на нажатие левой и правой кнопок мыши в клиентской области окна, а также на нажатие клавиш. При нажатии левой кнопки в клиентскую область окна, начиная с текущих координат курсора мыши, выводится строка "Нажата левая кнопка", а при нажатии правой кнопки - "Нажата правая кнопка".

При нажатии на левую и правую кнопки соответственно генерируются сообщения WM_LBUTTONDOWN и WM_RBUTTONDOWN, и им соответствуют обработчики с прототипами:

afx_msg void OnLButtonDown(UINT Flags, CPoint Loc);

afx_msg void OnRButtonDown(UINT Flags, CPoint Loc);

Первый параметр указывает на то, была ли при генерации сообщения нажата какая-нибудь клавиша или кнопка мыши. Этот параметр нас не будет пока интересовать. Второй параметр определяет координаты курсора мыши во момент нажатия кнопки. Класс CPoint порождается от структуры POINT, определенной так:

typedef struct tagPOINT {

LONG x;

LONG y;

} POINT;

Таким образом, мы легко можем определить координаты для вывода текстовой строки.

Обработчик сообщения WM_CHAR имеет прототип:

afx_msg void OnChar(UINT Char, UINT Count, UINT Flags);

Нас здесь будет интересовать только первый параметр. Он представляет собой ASCII-код символа, соответствующего нажатой клавише. При нажатии несимвольных клавиш сообщение WM_CHAR не посылается.

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]