Простые типы 6 страница

Функция SetAt() — член класса CMapStringToString — принимает в качестве аргументов ключ и ассоциированное с ним значение. Если такой ключ уже имеется в карте отображения, функция заменяет ассоциированное с ним значение тем значением, которое передано в качестве второго аргумента.

9.9.32. Извлечение значения из карты ассоциации
Диалоговое окно Get Map Value появляется на экране после щелчка на поле окна приложения. Так что нет ничего удивительного в том, что анализ программы мы начнем с функции OnLButtonDown() — члена класса представления. Ее текст представлен в листинге 4.9.
Листинг 4.9 Функция CMapView::OnLButtonDown()
void CMapView:OnLButtonDown(UINT nFlags, CPoint point)
// Сформировать и инициализировать диалоговое окно.
GetMapDIg dialog(this);
dialog.m_key = "";
// Вывести на экран диалоговое окно.
int result = dialog DoModal();
// Если пользователь щелкнул на кнопке ОК...
if (result == IDOK)
// Просмотр запрошенных данных.
CString value;
BOOL found = map. Lookup(dialog.m_key, value);
if (found)
MessageBox(value);
else
MessageBox("No matching value. ");
}
CView::OnLButtonDown(nFlags, point);
}

В функции OnLButtonDown(), как мы не раз видели в этой главе, организуется вывод на экран диалогового окна и ожидается, пока пользователь завершит с ним работу и щелкнет на ОК. Затем вызывается функция Lookup() класса ассоциированного списка, которая использует введенное значение ключа в качестве первого аргумента. Второй аргумент — это ссылка на строку-приемник, в которую функция перешлет найденное значение, ассоциированное с ключом. Если ключ не будет найден в объекте ассоциации, функция вернет FALSE, в противном случае — TRUE. Вызывающая программа использует возвращаемое значение с единственной целью — чтобы решить, что выводить на экран: содержимое строки-приемника, заполненное Lookup(), или окно предупреждающего сообщения.

9.9.33. Последовательный перебор элементов карты ассоциации
Для того чтобы вывести на экран содержимое объекта класса ассоциированного списка, программа должна последовательно перебрать все элементы карты ассоциации. Так же, как и в приложениях, демонстрирующих возможности массивов и списков, эта задача в приложении Map возлагается на функцию OnDraw(), текст которой представлен в листинге
4.10.
Листинг 4.10. Функция CMapView::OnDraw()
void CMapView::OnDraw(CDO *pDC)
{
CMapDoc* pDoc = GetDocument();

ASSERT_VALID(pDoc);

TEXTMETRIC textMetric;

pDC->GetTextMetrics(&textMetric);

int fontHeight = textMetric.tmHeight;,

int displayPosit ion = 10;

POSITION pos = map.GetStartPosition();

CString key;
CString value;

whi le (pos!= NULL)
{
map.GetNextAssoc(pos, key, value);
CStnng str = "Key " + key +
" is associated with the value " + value + "";
pDC->TextOut(10, displayPosition, str);
displayPosition += fontHeight;
Многое в этой версии очень напоминает другие версии, которые уже анализировались нами ранее в этой главе. Начинается процесс с вызова функции GetStartPosition() — члена класса ассоциированного списка, которая возвращает позицию первого элемента карты ассоциации (это может быть совсем не тот элемент, который был первым по времени вставлен в карту). Сам по себе обход организован в виде цикла while. В каждом очередном цикле вызывается функция GetNextAssoc(), одним из аргументов которой является ссылка на позицию текущего элемента — локальную переменную pos. В первом цикле используется значение позиции, возвращенное функцией GetStartPosition(). Функция же GetNextAssoc() извлекает ключ и значение из текущего элемента карты и переставляет позицию на следующий элемент. Когда программа доходит до последнего элемента узла, в переменной роз оказывается NULL и цикл обхода завершается.

9.9.34. Шаблоны класса коллекций
В библиотеку MFC включены шаблоны класса, с помощью которых можно создавать собственные специальные классы коллекций. Более подробная информация о шаблонах содержится в соответствующем разделе главы 26. Хотя сама по себе тема шаблоны в C++ достаточно объемна, использование шаблонов в этом конкретном случае — по отношению к классам коллекций — не вызывает особых затруднений. Предположим, вы хотите сформировать класс массива, который смог бы включать в качестве элементов массива структуры, приведенные в листинге 4.11.
Листинг 4.11. Пример структуры
struct MyValues
{
int value1;
int value2;
int value3;
};

Сначала для создания нового класса необходимо использовать шаблон:
CArray<MyValues, MyValues&> myValueArray;
Здесь CArray — это шаблон, который используется для создания собственного класса массива. Два аргумента шаблона — тип данных, который нужно хранить в массиве, и тип данных, который функции-члены нового класса массива должны использовать в качестве аргумента там, где это необходимо. В нашем случае тип данных, хранящихся в массиве,— это структуры MyValues. Второй же аргумент шаблона указывает, что функции-члены нового класса массива должны использовать в качестве аргумента ссылку на структуру типа MyValues.
Для формирования самого массива нужно установить его начальный размер:
myValueArray.SetSize(10, 5),
Теперь можно позволить себе добавлять элементы в этот массив:
MyValues myValues,
myValueArray.Add(myValues);
Поскольку новый класс массива сформирован по шаблону, этот массив можно использовать так же, как любой объект класса массивов MFC (что уже было описано выше). Другие шаблоны класса коллекций MFC, которые можно спокойно использовать в своих разработках, — это CList и СМар. Что же из всего сказанного следует? А следует то, что в вашем распоряжении, когда вы создаете собственные классы подобного типа, теперь оказываются результаты той гигантской работы, которую проделали программисты, создававшие MFC. Вы можете построить массив объектов класса Employee (Служащие) или связный список из объектов класса Order (Заказы) или карту ассоциации, в которой связываются имена с объектами класса Customer (Покупатели).


9.9.35 Класс CString
Едва ли найдется программа, в которой не обрабатывались бы тем или иным образом текстовые строки К сожалению, сам по себе язык C++ не имеет мощного встроенного механизма работы с данными такого типа, что позволяет некоторым программистам говорить о его "недоразвитости" по сравнению с PASCAL или BASIC. Встроенный в MFC класс CStn ng переводит подобные рассуждения в разряд злопыхательских инсинуаций. Методы этого класса ни в чем не уступают аналогичным средствам других языков. В табл. 4.3 перечислены чаще всего употребляемые методы этого класса.

Помимо перечисленных функций, в классе CString определен полный набор терминальных операторов для работы с текстовыми строками. С их помощью можно выполнять конкатенацию (т.е. объединение, слияние) строк. Оператор (+) присваивает строке новое значение, оператор (=) выполняет преобразование машинного формата строки (например, получает так называемый С-стиль), используя оператор LPCTSTR, и т.п.
Формирование объекта класса CString выполняется стандартным для языка C++ способом:
CString str = " This is test string",
Конечно, существует много способов формирования подобного объекта. Наш пример демонстрирует только один из возможных вариантов. Можно создать пустой объект и позже присвоить ему некоторое значение либо создать объект, копируя существующий или заказав n-кратное повторение некоторого символа.
Когда экземпляр класса создан, можно вызывать методы класса и манипулировать строкой, как вам вздумается. Например, можно преобразовать все символы строки в прописные (символы верхнего регистра):
str. MakeUpper();
Для того чтобы удлинить строку, можно воспользоваться переопределенными терминальными операторами (+) и (+=):
CString sentence = "hel lo " + str;
sentence += "there.";
Для сравнения двух строк нужно вызвать функцию-член класса: str. Compare ("Test String");
Можно также сравнивать два экземпляра класса CString: CString testStr = "Test String";
str.Compare(testStr);
А самый изящный вариант таков:
if(testStr == str)
Если вы полистаете оперативную документацию, то найдете массу примеров использования самых разнообразных методов класса CString. Можете поверить мне на слово, что использовать эти методы не сложнее, чем применять встроенные функции BASIC или PASCAL.

9.9.36 Классы для работы со временем
Если вам приходилось программировать обработку данных, связанных с текущим временем, которые можно получить с компьютера, вас, несомненно, порадует наличие в MFC таких классов, как CTime и CTimeSpan. Они представляют соответственно абсолютное и относительное (elapsed) время. Использование этих классов настолько очевидно, что мы даже отказались от специального примера в данном разделе. Тем не менее определенные начальные сведения об этих полезных классах вы из него почерпнете. Прежде чем приступить к самостоятельным экспериментам с классами времени, взгляните на табл. Е.5, в которой перечислены методы класса Ctime, и на аналогичную таблицу для класса СТimeSpan (табл.4.4).

9.9.36.1 Использование объекта класса СТime
Для создания объекта класса CTime нужно просто вызвать функцию GetCurrentTime(): CTime time = CTime::GetCurrentTime();

Поскольку GetCurrentTime() является статической функцией класса CTime, ее можно вызывать без предварительного создания экземпляра класса. Но имя класса нужно обязательно включить в оператор вызова. Как видно, функция возвращает объект класса СТime, содержимое которого соответствует текущему времени. Если нужно вывести отсчет времени на экран, придется обратиться к функции Format
():

CStnng str = time. Format ("DATE: %A, %B %d, %Y");
Функция Format() требует в качестве единственного аргумента форматную строку, которая определяет вид выходного текста. Предыдущий пример сформирует такой текст:
DATE: Saterday, April 20, 1996
Форматная строка для Format() строится примерно по таким же правилам, что и аналогичный аргумент всем известной функции printf() для работы в DOS или функции wsprintf() для работы в Windows. В нее также включаются литералы, знаки препинания, например "DATE:" в нашем примере, и форматирующие символы, которые затем замещаются значениями. Форматирующий символ %А в предыдущем примере заменяется наименованием дня недели, а %В — наименованием месяца. Таким образом, разница состоит только в форматирующих символах. Символы, которые используются в функции Format(), перечислены в табл.
Код Описание
%а Сокращенное наименование дня недели, например Sat вместо Saturday
%A Полное наименование дня недели
%b Сокращенное наименование месяца, например Mar вместо March
%В Полное наименование месяца
%с Дата и время в формате, соответствующем локализованной версии продукта Например, для США это будет выглядеть так 03/17/96 12:15:34
%d День месяца как число (01-31)
%Н Часы в сутках (00-23)
%I Часы в 12-часовом формате (01-12)
%j День в году - число (001-366)
%m Месяц как число (1-12)
%М Минуты как число (00-59)
%р Локализованное представление в 12-часовом формате (А М /Р М)
%S Секунды как число (00-59)
%U Неделя в году как число (00-51, полагается, что воскресенье — первый день очередной недели)
%w День недели как число (0-6, полагается, что воскресенье имеет номер 0)
%W Неделя в году как число (00-51, полагается, что понедельник — первый день очередной недели)
%х Локализованное представление даты
%X Локализованное представление времени
%у Год без первых двух цифр, соответствующих столетию (00-99)
%y Год без первых двух цифр, соответствующих столетию (00-99)
%Y Год полностью — с префиксом столетия
%z Сокращенное имя временной зоны
%Z Полное имя временной зоны
%% Знак процента
Другие методы класса Ctime, такие как GetMmute(),GetMonth(),GetYear(), в комментариях не нуждаются. Однако мы все-таки покажем пример использования метода GetLoca ITm():
struct tm* timeStruct,
timeStruct - time GetLocaITm(),
В первом операторе объявляется указатель на структуру tm. Сама структура объявлена в Visual C++, а текст объявления приведен в листинге Е 14. Во втором операторе этому указателю присваивается значение, возвращаемое функцией GetLocalTm(), причем соответствующая структура уже будет заполнена данными.
Листинг 4.12 Структура tm
struct tm
{
int tm_sec, /* секунды после минут - [0,59] */
int tmjnm, /* минуты после часа - [0,59] */
int tm_hour, /* часы после полуночи - [0,23] */
int tm_mday, /* день месяца - [1,31] */
int tmjnon; /* месяц - [0,11] */
int tm_year; /* год, начиная с 1900 */
int tm_wday, /* день недели, начиная с воскресенья - [0,6] */
int tm_yday; /* день, начиная с 1-го января - [0,365] */
int tm_isdst; /* флаг половины суток */
Класс CTime располагает множеством перегруженных конструкторов, которые позволяют создавать экземпляры класса самыми различными способами, используя самые
различные варианты представления времени.

9.9.36.2 Использование объекта класса CTimeSpan
Объект класса CTimeSpan есть не что иное как разница между двумя отсчетами времени. Можно использовать объект класса CTime вместе с объектом класса CTimeSpan, чтобы определить, сколько времени прошло между двумя отсчетами. Сначала нужно создать объект класса CTime для текущего времени. Затем, когда нечто свершится, нужно создать второй объект класса СТime для нового отсчета. Вычитание нового объекта класса из старого СТime породит объект класса CTimeSpan, который и будет содержать данные о временном промежутке между отсчетами. Пример подобной программки приведен в листинге 4.13.
Листинг 4.13. Определение временного интервала
CTime startTime = CTime::GetCurrentTime();
//..
//..
//..
CTime endTime = CTime::GetCurrentTime();
CTimeSpan timeSpan = endTime - startTime;

9.10 Программы на VISUAL C++

9.10.1 ВВЕДЕНИЕ

Программа, созданная Visual C++ АррWizard, состоит из четырех основных частей: объекта приложения, объекта главного окна, объекта документа и объекта вида.
Объект приложения
Объект приложения, находящийся в файлах welcome.h и welcome.cpp (файл.h содержит определения констант, а также объявления переменных и методов класса),
то, что Windows запускает при старте программы. Когда этот объект начинает
работу, он размещает на экране главное окно.
Объект главного окна
Объект главного окна отображает на экране саму программу; в нем находится
меню, заголовок окна и панель инструментов. Объект главного окна отвечает за
все, что происходит вокруг того места, где собственно работает наша программа
(где она рисует, выводит текст и т. д.). Рабочая зона программы называется клиентской областью окна; например, текст выводится в клиентской области текстового редактора. За работу с клиентской областью отвечает объект вида.
Объект вида
Объект вида предназначен для работы с клиентской областью — местом, где обычно отображаются в соответствующем формате данные нашей программы (скажем, текст, если вы работаете с текстовым редактором). На самом деле объект вида представляет собой окно, которое накладывается поверх клиентской области. Объект вида отображает данные, хранящиеся в объекте документа.
Объект документа
В объекте документа хранятся данные программы.
Visual C++ облегчает задачу и позволяет сохранить все данные в объекте документа, а затем поручить объекту вида отобразить лишь те данные, которые
попадают в клиентскую область объекта вида. Как мы вскоре увидим, для одного
документа можно иметь несколько одновременно открытых видов.
Взаимосвязь четырех частей программы на Visual C++ выглядит так:

9.10.2.Вывод приветствия

Пока что мы рассматривали программу, написанную мастером АррWizard. Давайте
изменим ее так, чтобы она выводила сообщение «Добро пожаловать в Visual C++!»
Для этого мы добавим небольшой фрагмент кода в метод OnDraw() класса CWelcomeView
(вспомните, что этот класс служит для отображения данных). Программа вызывает
метод OnDraw(), когда ей требуется вывести что-либо в клиентской области программы (например, при запуске программы, при свертывании и восстановлении окна или при перемещении другого окна, закрывающего часть клиентской области). В данный момент метод OnDraw() выглядит так:
void CWelcomeView::OnDraw(CDС* pDC)
{
CWelcomeDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
// TODO: добавьте код для отображения данных
}
Мы добавим в этот метод код для вывода сообщения.
1. Чтобы приступить к редактированию метода, перейдите в окне просмотра
Visual C++ на вкладку ClassView.
2. Найдите в иерархическом списке название класса CWelcomeView.
3. Щелкните на знаке «плюс» рядом с элементом. На экране выводится список
методов данного класса.
4Найдите в списке метод OnDraw() и дважды щелкните на нём - метод откроется в текстовом редакторе.
5. Чтобы изменить поведение нашей программы, добавьте в OnDraw() всего две
строки:
void CWelcomeView::QnDraw(CDC* pDC)
{
CString welcome_string = "Добро пожаловать в Visual C++";
CWelcomeDoc* pDoc = GetDocument();
ASSERT_VALID(pDoc);
pDC->TextOut(0, 0, welcome_string);
}

Рис. 1.1. Редактирование метода OnDraw()
6. Программа готова. Запустите ее: для этого выполните команду Build > Build
welcome.exe, а затем — команду Build > Execute welcome.exe. Результат ее работы
показан на рис. 1.2.
7. Программа успешно выводит в окне сообщение. Настало время разобрать ее по кусочкам и понять, как она работает.

Рис. 1.2. Первая программа с окном

9.10.3. Исследуем объект приложения
При запуске приложения Windows вызывает функцию WinMain() объекта приложения, поэтому наше знакомство с программой начнется именно с объекта приложения. С нашей точки зрения объект приложения должен выполнять три задачи: запустить программу, создать главное окно и организовать передачу сообщений Windows в главное окно и из него.
Что такое «сообщения Windows»? Это особые сигналы с минимальным объемом
служебных данных, посредством которых различные объекты в среде Windows
общаются между собой. Например, когда пользователь завершает работу программы, Windows посылает объекту приложения сообщение WM_QUIT. Если же пользователь изменяет размеры окна программы, она получает сообщение WM_SIZE.Наиболее интересные сообщения Windows перечислены в табл. 1.1.

Oбъект приложения отсылает большинство полученных сообщений объекту главного окна (не считая WM_QUIT, которое завершает работу объекта приложения).
Объекты в программе на Visual C++ интенсивно общаются друг с другом. Это вполне понятно, поскольку программа делится на четыре главных объекта и каждому из них иногда приходится обращаться к услугам других объектов.
Код объекта приложения содержится в файле welcome.cpp. Наибольший интерес
для нас представляет метод InitInstance(), поскольку именно в нем программа
собирает остальные классы (главного окна, документа и вида) и объединяет их в
шаблон документа, в соответствии с которым объект приложения организует работу программы:
BOOL CWelcomeApp::lnitlnstance()
{
AfxEnableControlContainer();
// Стандартная инициализация
// Если вы не пользуетесь какими-либо функциями и желаете
// сократить размер выполняемого файла, удалите ненужные процедуры инициализации.
#ifdef _AFXDLL
Enable3dControls(); // Вызывается при использовании
// MFC в виде совместной DLL
#else
Enable3dControlsStatic(); // Вызывается при статической
// компоновке MFC
#endif
// Изменить ключ реестра, под которым будут сохраняться
// параметры. Замените строку более подходящей, например,
// названием вашей компании или организации.
SetRegistryKey(_T("Local AppWizard-Generated Applications"));
LoadStdProfileSettings(); // Загрузить стандартные параметры
// из INI-файла (включая MRU)
// Зарегистрировать шаблоны документов приложения.
// Шаблоны документов объединяют документы, обрамленные окна и виды.
CSingleDocTemplate* pDocTemplate;
pDocTemplate = new CSingleDocTemplate(
IDR_MAINFRAME,
RUNTIME_CLASS(CWelcomeDoc),
RUNTIME_CLASS(CMainFrame), // Главное обрамленное окно SDI
RUNTIME_CLASS(CWelcomeView));
AddDocTemplate(pDocTemplate);
// Просмотреть командную строку в поисках стандартных команд оболочки,
// DDE и открытия файлов
CCommandLinelnfo cmdlnfo;
ParseCommandLirie(cmdlnfo);
// Организовать обработку команд, содержащихся в командной строке
if (!ProcessShellCommand(cmdlnfo))
return FALSE;
// Было инициализировано всего одно окно; отобразить и обновить его.
M_pMainWnd->ShowWindow(SW_SHOW);
m_pMainWnd->UpdateWindow();
return TRUE;
}
Обратите также внимание на строку m_pMainWnd - >SnowWindow(SW_SHOW); в конце метода InitUnstance(). Именно в ней наш объектприложентя отображает главное окно программы, вызывая метод ShowWindow() объекта главного окна. Переменная
m_pMainWnd содержит указатель на объект главного окна, а оператор -> действует
точно так же, как и оператор. («точка»), только он работает с указателем на
объект. Другими словами, этот оператор обращается к переменным и методам
того объекта, на который ссылается данный указатель.
Имена переменных классов в Visual C++ имеют стандартный префикс m_. На самом деле в Visual C++ аналогичные префиксы используются для всех имен переменных (так называемая «венгерская запись»). Префикс обозначает тип переменной; например, префикс с используется для символьных типов, поэтому с первого взгляда становится ясно, что cInput — символьная переменная. Наиболее распространенные префиксы венгерской записи перечислены в табл. 1.2.
Префикс Значение
а Массив
b Логический тип (int)
by Беззнаковый символьный тип (byte)
с Символьный тип
cb Счетчик байтов
cr Цвет
сх, су Короткий тип (short)
dw Беззнаковый длинный тип (dword)
fn Функция
h Логический номер (handle)
i Целое
M_ Переменная класса
n Short или int
np Ближний указатель
P Указатель
l Длинный тип (long)
IP Длинный указатель
s Строка
sz Строка, заканчивающаяся нуль-символом
tm Текстовая метрика
w Беззнаковое целое (word)
x. у Короткий тип (координата х или у)
Исходный текст объекта приложения находится d файлах welcome.h/welcome.cpp.
welcome.h и welcome.cpp
// welcome.h: главный заголовочный файл для приложения WELCOME
//
#if!defined(AFX_WELCOME_H__AF072C83_900A_11DO_8860_444553540000__
INCLUOED_)
#define AFX_WELCOME_H__AF072C83_900A_11DO_8860_444553540000__INCLUDED_
#if _MSC_VER >= 1000
#pragma once
#endif // _MSC_VER >= 1000
#ifndef __AFXWIN_H__
#error include "stdafx.h" before Including this file for PCH
#endif
#include "resource.h" // основные символические константы
///////////////////////////////////////////////////////////////////////
// CWelcomeApp:
// Реализация этого класса содержится в файле welcome.cpp
//
class CWelcomeApp: public CWinApp
{
public:
CWelcomeApp;
// Переопределения
// Переопределения виртуальных функций, сгенерированные ClassWizard
//{{AFX_VIRTUAL(CWelcomeApp)
public:
virtual BOOL InitlnstanceO;
//}}AFX_VIRTUAL
// Реализация
//{{AFX_MSG(CWelcomeApp)
afx_msg void OnAppAboutO;
// ВНИМАНИЕ - здесь ClassWizard вставляет и удаляет функции класса.
// НЕ ИЗМЕНЯЙТЕ содержимое этих частей сгенерированного кода!
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};

////////////////////////////////////////////////////////////////////////
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ вставляет дополнительные объявления
// перед предшествующей строкой.
#endif
//
!defined(AFX__WELCOME_H__AF072C83_900A_11DO_8860_444553540000__INCLUDED_)
// welcome.cpp: определяет поведение классов данного приложения.
//
#include "stdafx.h"
ffinclude "welcome.h"
#include "MainFrm.h"
#include "welcomeDoc.h"
#include "welcomeView.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////
// CwelcomeApp
BEGIN_MESSAGE_MAP(CWelcomeApp, CWinApp)
//{{AFX_MSG_MAP(CWelcomeApp)
ON_COMMAND(ID_APP_ABOUT, OnAppAbout)
// ВНИМАНИЕ - здесь ClassWizard добавляет и удаляет макросы схемы.
// НЕ ИЗМЕНЯЙТЕ содержимое этих частей сгенерированного кода!
//}}AFX_MSG_MAP
// Стандартные файловые команды документа
ON_COMMAND(ID_FILE_NEW, CWinApp::OnFileNew)
ON_COMMAND(ID_FILE_OPEN, CWinApp::OnFileOpen)
// Стандартная команда настройки принтера
ON_COMMAND(1D_FILE_PRINT_SETUP, CWinApp::OnFilePrintSetup)
END_MESSAGE_MAP()
////////////////////////////////////////////////////////////////////////
// Конструктор CWelcomeApp
CWelcomeApp::CWelcomeApp()
{
// TODO: добавьте код конструктора,
// Инициализация наиболее важных переменных и функций
// должна выполняться в Initlnstance
}
/////////////////////////////////////////////////////////////////////////
// Единственный объект класса CWelcomeApp
CWelcomeApp theApp;
/////////////////////////////////////////////////////////////////////////
// Инициализация CWelcomeApp
BOOL CWelcomeApp::lnitlnstance()
{
AfxEnableControlContainer();
// Стандартная инициализация
// Если вы не пользуетесь какими-либо функциями и желаете
// сократить размер выполняемого файла, удалите
// ненужные процедуры инициализации.
#ifdef _AFXDLL
EnableSdControlsQ: // Вызывается при использовании
// MFC в виде совместной DLL
#else
Enable3dControlsStatic(); // Вызывается при статической
// компоновке MFC
#endif
// Изменить ключ реестра, под которым будут сохраняться
// параметры. Замените строку более подходящей, например,
// названием вашей компании или организации.
SetRegistryKey(_T("Local AppWizard-Generated Applications"));
LoadStdProfileSettings(); // Загрузить стандартные параметры
// из INI-файла (включая MRU)
// Зарегистрировать шаблоны документов приложения.
// Шаблоны документов объединяют документы, окна и виды.
CSingleDocTemplate* pDocTemplate;

pDocTemplate = new CSingleDocTemplate(

IDRJWINFRAME,

RUNTIME_CLASS(CWelcomeDoc),

RUNTIME_CLASS(CMainFrame), // Главное окно SDI
RUNTIME_CLASS(CWelcomeView));
AddDocTemplate(pDocTemplate);
// Просмотреть командную строку в поисках стандартных команд оболочки,
// DDE и открытия файлов
CCommandLinelnfo cmdlnfo;
ParseCommandLine(cmdInfо);
// Организовать обработку команд, содержащихся в командной строке
if (! ProcessShellCommand(cmdlnfo))
return FALSE;
// Было инициализировано всего одно окно; отобразить и обновить его.
m_pMainWnd->ShowWindow(SW_SHOW);
m_pMainWnd->UpdateWindow();
return TRUE;
///////////////////////////////////////////////////////////////////////
Окно диалога CAboutDlg, отображаемое командой About
ass CAboutDlg: public CDialog
blic:
CAboutDlg();
Диалоговые данные
//{{AFX_DATA(CAboutDlg)
enum { IDD = IDD_ABOUTBOX };
//}}AFX_DATA
// Переопределения виртуальных функций, сгенерированные ClassWizard
//{{AFX_VIRTUAL(CAboutDlg)
protected;
virtual void DoDataExchange(CDataExchange* pDX); // Поддержка DDX/DDV
//}}AFX_VIRTUAL
// Реализация
protected:
//{{AFX_MSG(CAboutDlg)
// Обработчики сообщений отсутствуют
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};

CAboutDlg::CAboutDlg(): CDialog(CAboutDlg::IDD)
{
//{{AFX_DATA_INIT(CAboutDlg)
//}}AFX_DATA_INIT
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CAboutDlg)
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
//{{AFX_MSG_MAP(CAboutDlg)
// Обработчики сообщений отсутствуют
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
// Команда приложения для вызова окна диалога
void CWelcomeApp::OnAppAbout()
{
CAboutDlg aboutDlg;
aboutDlg.DoModal();
}
////////////////////////////////////////////////////////////////////////
// Команды CWelcomeApp
После первого знакомства с объектом приложения нашей программы займемся
объектом главного окна, поскольку одна из важнейших задач объекта приложения —
разместить это окно на экране.

9.10.4. Исследуем объект главного окна

Объект главного окна отвечает за всю работу окна программы, за исключением
клиентской области.

Это означает, что объект главного окна отвечает за заголовок, строку меню, панель
инструментов и строку состояния в нижней части окна. Заголовок и строка меню
создаются автоматически при создании окна, а панель инструментов и строка состояния добавляются в методе OnCreate(). В файле MainFrm.cpp это делается так:
Это означает, что объект главного окна отвечает за заголовок, строку меню, панель
инструментов и строку состояния в нижней части окна. Заголовок и строка меню
создаются автоматически при создании окна, а панель инструментов и строка состояния добавляются в методе OnCreate(). В файле MainFrm.cpp это делается так:
int CMainFrame::OnCreate(LPCREATESTRUCT IpCreateStruct)
{
if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
return -1;
if (!m_wndToolBar.CreateEx(this, TBSTYLE_FLAT, WS_CHILD |
WS_VISIBLE | CBRS_TOP | CBRS_GRIPPER |
CBRSJTJOLTIPS | CBRS_FLYBY |
CBRS|SIZE_DYNAMIC) ||
!m_wndToolBar.LoadToolBar(IDR_MAINFRAME))
{
TRACEOC'Failed to create toolbar\n");
return -1; // неудачная попытка создания
}
if (!m_wndStatusBar.Create(this)))
!m_wndStatusBar.Setlndicators(indicators,
sizeof(indicators)/sizeof(DINT)))
{
TRACEOC'Failed to create status bar\n");
return -1; // неудачная попытка создания
}
// TODO: Удалите следующие три строки, если вам не нужна
// закрепляемая панель инструментов
m_wndToolBar.EnableDocking(CBRS_ALIGN_ANY);
EnableDocking(CBRS_ALIGN_ANY);
DockCont rolBar(&m_wndToolBa r);
return 0;
}
Хотя меню и панель инструментов отображаются объектом главного окна, в нем
почти нет кода для выполнения этой задачи. Основная часть текста программы сосредоточена в объекте вида — окне, которое накрывает клиентскую область.
Главное окно также отображает объект вида, поэтому после краткого знакомства
с объектом главного окна мы рассмотрим сам объект вида. Исходный текст объекта
главного окна находится в файлах MainFrm.h/MainFrm.cpp.
MainFrm.h и MainFrm.cpp
// MainFrm.h: интерфейс класса CMainFrame
//
/////////////////////////////////////////////////////У///////////////////
#if!defined(AFX_MAINFRM_H__AF072C87_900A_11DO_8860_444553540000__


Понравилась статья? Добавь ее в закладку (CTRL+D) и не забудь поделиться с друзьями:  



double arrow
Сейчас читают про: