- •О.С. Зеленський
- •Розділ 1. Загальні відомості створення додатку windows
- •1.1. Створення додатку Windows за допомогою майстра AppWizard
- •1.2. Варіанти майстрів для різних проектів
- •1.3. Короткий опис sdi програми
- •1.4. Короткий опис mdi програми
- •1.5. Короткий опис простого діалогового додатку
- •Контрольні питання
- •Розділ 2. Повідомлення і команди
- •2.1. Обробка повідомлень
- •2.2. Цикли обробки повідомлень
- •2.3. Карти повідомлень
- •Контрольні питання
- •Розділ 3. Документи та види
- •3.1. Клас додатку
- •3.2. Клас головного вікна
- •3.3. Клас документа
- •3.4. Класи виду
- •Контрольні питання
- •Розділ 4. Робота з клавіатурою, мишею і меню
- •4.1. Робота з клавіатурою
- •4.2. Робота з мишею
- •4.3. Робота з меню
- •Контрольні питання
- •Розділ 5. Виведення на екран
- •5.1. Класи графічних об'єктів
- •5.2. Робота зі шрифтами
- •5.3. Робота з пензликами та малювання графічних фігур
- •5.4. Робота з пензликом
- •5.5. Робота зі скролінгом
- •5.6. Приклад роботи з таблицями
- •5.7. Малювання на екрані маніпулятором "миша"
- •5.8. Завантаження та виведення на екран бітових зображень
- •5.9. Копіювання бітових образів
- •5.10. Малювання графічних об'єктів з використанням резинових контурів та метафайлів
- •5.11. Виділення графічних об'єктів у прямокутній області
- •5.12. Універсальний приклад роботи з двовимірною графікою з використанням резинового контуру
- •5.13. Запис на диск та зчитування з диску графічних об'єктів
- •5.14. Побудова кругових діаграм і гістограм
- •5.15. Користувацький режим роботи з графікою на прикладі малювання годинника Clock
- •Контрольні питання
- •Завдання
- •Розділ 6. Друк і попередній перегляд документів
- •6.1. Вибір і налаштування параметрів друку
- •6.2. Створення контекста пристрою
- •6.3. Друк документів і бібліотека mfc
- •6.4. Масштабування
- •6.5. Друк багатосторінкового документа
- •Контрольні питання
- •Розділ 7. Робота з файлами
- •7.1. Приклад роботи з файлами на основі класів cFile, cStdioFile та потоку fstream
- •7.1.1. Робота з класом cFile
- •7.1.2. Робота з потоком fstream
- •Можливі режими доступу
- •7.1.3. Робота з класом cStdioFile
- •7.2. Серіалізація даних, клас cArchive
- •7.3. Використання реєстру в додатках
- •Контрольні питання
- •Завдання
- •Розділ 8. Діалогові вікна
- •8.1. Створення діалогового вікна та простіші елементи керування
- •8.2. Робота зі списками і комбінованими полями
- •8.3. Ускладнений приклад зі списками
- •8.4. Робота з повзунками
- •8.5. Виведення бітових матриць в діалозі та у вікні виду
- •8.6. Лінійний регулятор, лінійний індикатор, інкриментний регулятор
- •8.7. Стандартні діалоги вибору файлів, шрифтів та кольору
- •8.8. Взаємоз'вязок діалога, документа та виду при розробці додатку
- •8.8.1. Клас cDialDoc
- •8.8.2. Клас cDialView
- •8.8.3. Клас Cdlg
- •8.9. Формування вхідного документа на основі діалогу
- •Контрольні питання
- •Завдання Робота з типовими елементами керування
- •Робота зі списками і комбінованими полями
- •Список літератури
8.8. Взаємоз'вязок діалога, документа та виду при розробці додатку
Повна реалізація прикладу знаходиться у папці DISK\dialog\dialog9. Окремі частини реалізації прикладу знаходяться у папках DISK\dialog\dialog7, DISK\dialog\dialog8.
Створимо додаток з назвою dialog з архітектурою документ-вид. Отримаємо класи CDialDoc – документу, CDialView – виду. Клас Cdlg створимо пізніше. В додатку будемо вести картотеку автомобілів, в папці BMP будемо зберігати фотографії машин. Через клас діалогу можна буде отримати та редагувати інформацію про машину. У файлі dia.ini буде зберігатись структура з останніми настройками програми, цей файл буде бінарним. На рис. 8.15 показано схему роботи цього додатку:
Рис. 8.15. Схема роботи додатку dialog
Стрілками на рисунку показано рух інформації між класами та файлами.
8.8.1. Клас cDialDoc
Конструктор класу документа має наступний вид:
CDialDoc::CDialDoc()
{
strcpy(mas_mach[0],"Mazda RX-8");
strcpy(mas_mach[1],"ZAZ Lanos");
strcpy(mas_mach[2],"Mercedes-Benz SLR");
strcpy(mas_mach[3],"Opel Astra Sedan");
strcpy(mas_mach[4],"Audi A3 Cabriolet");
strcpy(mas_mach[5],"ВАЗ-3116");
strcpy(mas_mach[6],"ГАЗ «Волга»");
strcpy(mas_mach[7],"BMW M3");
strcpy(mas_mach[8],"Peugeot 207");
strcpy(mas_mach[9],"Land Rover Range");
strcpy(mas_mach[10],"Жигули");
mas_st [0]=25400;
mas_st [1]=12000;
mas_st [2]=600000;
mas_st [3]=25100;
mas_st [4]=28000;
mas_st [5]=10000;
mas_st [6]=11000;
mas_st [7]=71900;
mas_st [8]=19500;
mas_st [9]=124660;
mas_st [10]=5100;
CString str,str1;
CString mash[11]={"mazda","zaz_lanos","mersedes","opel",
"audi", "VAZ", "GAZ","BMW", "peugeot",
"Land Rover", "zhigyli"};
if(access("BMP",0))
AfxMessageBox("Отсутствует папка BMP, где должны находиться файлы *.bmp",
MB_ICONINFORMATION);
else
{
for(int i=0;i<11;i++)
if(access("BMP\\"+mash[i]+".bmp",0))
str = str + "- " + mash[i] + ".bmp\n";
if(str.GetLength())
{
CString str1('-',60);
str1+="\n";
str = "В папке BMP отсутствуют следующие файлы:\n" +str1 +str;
AfxMessageBox(str,MB_ICONINFORMATION);
}
}
start = true;
dia.kol_mach = 0;
}
В ньому заповнюються дані про назви автомобілів, та їх вартості. Функцію access використовуємо для перевірки існування папки BMP. Якщо папка не існує, то виведемо на екран напис, який повідомляє що папка не знайдена та виходимо з функції. Змінна str типу CString слугує для створення повідомлення, яке буде виводитись при відсутності потрібних файлів зображень у папці BMP. Змінна str1 потрібна для додавання до тексту повідомлення рядка із лініями.
При відкритті документа опції будуть зчитуватись із файлу dia.ini:
BOOL CDialDoc::OnNewDocument()
{
Ini_str();
if (OnOpenDocument("dia.ini")) SetTitle("dia.ini");
if (!CDocument::OnNewDocument()) return FALSE;
return TRUE;
}
Функція Ini_str встановлює настройки за умовчанням, які будуть потрібні при створенні діалогу з настройками:
void CDialDoc::Ini_str()
{
SetModifiedFlag();
dia.color = 0;
dia.kol_mach = 1;
dia.marka = 0;
dia.god = 0;
dia.sost = 0;
dia.probeg = 0;
dia.kond = 0;
dia.signal = 0;
dia.val = 0;
dia.grn = 5.05;
dia.euro = 0.65;
dia.color_viv = RGB(255,0,0);
dia.logFont.lfHeight = -20;
dia.logFont.lfWidth = 0;
dia.logFont.lfEscapement = 0;
dia.logFont.lfOrientation = 0;
dia.logFont.lfWeight = FW_NORMAL;
dia.logFont.lfItalic = 0;
dia.logFont.lfUnderline = 0;
dia.logFont.lfStrikeOut = 0;
dia.logFont.lfCharSet = ANSI_CHARSET;
dia.logFont.lfOutPrecision = OUT_DEFAULT_PRECIS;
dia.logFont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
dia.logFont.lfQuality = PROOF_QUALITY;
dia.logFont.lfPitchAndFamily = VARIABLE_PITCH|FF_ROMAN;
strcpy(dia.logFont.lfFaceName,"Times New Roman Cyr");
}
Ці настройки можуть зберігатись або зчитуватись через стандартну функцію класу документа Serialize:
void CDialDoc::Serialize(CArchive& ar)
{
dialog t1;
try {
if (ar.IsStoring())
{
ar.Write (&dia,sizeof(dia));
return;
}
if (!ar.IsStoring())
{
DWORD dl = sizeof(t1);
if(ar.GetFile()->GetLength() != dl)
{
AfxMessageBox("Нарушена структура файла!!!");
return;
}
ar.Read (&t1,sizeof(t1));
if( (t1.logFont.lfItalic > 1) ||
(t1.logFont.lfUnderline > 1) ||
(t1.logFont.lfStrikeOut > 1) ||
(t1.kond > 1) ||
(t1.signal > 1) ||
(t1.probeg < 0) ||
(t1.sost > 3))
{
AfxMessageBox("Нарушена структура файла!!!");
return;
}
} // зчитування
} // try
catch(...)
{
AfxMessageBox("Ошибка доступа при работе с файлом!!!");
return;
}
dia = t1;
}
Вхідним параметром функція приймає клас CArchive. Цей клас містить у собі функції для роботи з архівованими файлами, він використовує для роботи об’єкт класу CFile. Функція IsStoring класу CArchive перевіряє чи буде запис або зчитування з файлу. Функція Write записує дані у файл, а Read зчитує дані з файлу. Функція GetFile повертає вказівку на об’єкт файлу CFile. А функція GetLength класу повертає CFile розмір файлу. Отже при роботі функції ми або записуємо або зчитуємо структуру типу dialog. При зчитуванні робимо додаткові перевірки на розмір та правильність вхідних даних, у разі помилкових даних зчитування не відбувається.
Функція OnDialog створює клас діалогу з настройками:
void CDialDoc::OnDialog()
{
Cdlg di(dia,this);
if (di.DoModal() == IDOK)
{
dia = di.dial;
SetModifiedFlag();
}
this->UpdateAllViews(0);
}
Відразу при конструюванні діалогу ми передаємо вказівку this на клас CDialDoc, через яку будемо отримувати змінні для заповнення елемента списка IDC_LIST1 у функції OnInitDialog. Створюємо вікно діалогу функцією DoModal. Функцію SetModifiedFlag потрібно викликати якщо стались зміни даних документа. Вона встановлює внутрішній прапорець класу CDocument, який при закритті документа видасть повідомлення чи потрібно зберігати змінені дані на диск. Функція UpdateAllViews оновлює усі вікна виду.