Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Лабораторный практикум «Основы разработки приложений Windows» книга 1.DOC
Скачиваний:
107
Добавлен:
10.05.2014
Размер:
721.41 Кб
Скачать

Перекрашивание диалогового окна и его элементов

Обычно диалоговое окно имеет серый цвет, а строки текста, образующие статические элементы управления, по умолчанию выводятся черными. Windows предоставляет средства перекрашивания диалогового окна и содержащихся в нем элементов. Перекрашивание выполняется путем обработки сообщений WMCTLCOLORDLG (для перекрашивания самого диалогового окна),WMCTLCOLOR­STATIC (для перекрашивания фона статического элемента), WM­CTL­COLORLISTBOX (для перекрашивания фона окна списка) и некоторых других. Перекрашивание осуществляется довольно своеобразно: для того, чтобы перекрасить диалог или элемент управления в нем, функция обработки соответствующего сообщения должнавернутьдескриптор кисти требуемого цвета. Если эта кисть будет использоваться в различных местах программы неоднократно, ее лучше создать заранее, для чего более всего подходит функция обработки сообщенияWMINITDIALOG;если же она нужна только в одном месте, то ее можно там и создать. Таким образом, для перекрашивания фона диалогового окна в программу следует ввести такие фрагменты:

/*Пример 4-7. Перекрашивание окна диалога (фрагменты) */

/*Оконная функция диалогового окна*/

BOOL CALLBACK DlgProc(HWND hwnd,UINT msg,

WPARAM wParam,LPARAM lParam){

switch(msg) {

HANDLE_MSG(hwnd,WM_CTLCOLORDLG,DlgOnColorDlg);

default:

return FALSE;

}

}

/*Обработка сообщения WM_CTLCOLORDLG*/

HBRUSH DlgOnColorDlg(HWND,HDC,HWND,int){

return CreateSolidBrush(RGB(200,0,0));//Красная кисть

}

Все функции обработки сообщений о перекрашивании имеют одинаковый прототип и при передаче им управления (в результате поступления в приложение соответствующего сообщения) принимают четыре параметра:

HBRUSH DlgOnColorxxx(

HWND,//Дескриптор диалогового окна

HDC,//Дескриптор контекста диалогового окна

HWND,//Дескриптор конкретного элемента управления

int//Характерная константа

);

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

Наличие среди параметров функции DlgOnColorxxx()дескриптора контекста устройства данного элемента управления (второй параметр) позволяет изменять в нем цвет текста и фона под ним; наличие дескриптора конкретного элемента управления (третий параметр) позволяет по-разному обрабатывать сообщения, поступающие в однородные элементы управления. Однако здесь возникает осложнение. Мы различаем элементы управления не по их дескрипторам, которые нам обычно неизвестны, а по идентификаторам, которые назначаются элементам управления при их описании в файле ресурсов. Для того, чтобы по известному нам идентификатору получить дескриптор (и затем сравнить его со значением третьего параметра функцииDlgOnColorxxx())следует воспользоваться функциейGetDlgItem().

Рассмотрим обобщенный пример перекрашивания диалогового окна, содержащего два списка (рис. 4.8).

Рис. 4.8. Перекрашивание списков в диалоговом окне

Приведенный на рис. 4.8 диалог создается с помощью такого файла ресурсов:

Controls DIALOG 8, 15, 106, 70

CAPTION "Списки" {

CONTROL "", ID_LIST1, "listbox", WS_BORDER|WS_VSCROLL,

13, 10, 36, 52

CONTROL "", ID_LIST2, "listbox", WS_BORDER|WS_VSCROLL,

59, 10, 36, 52

}

Перекрасим окно левого списка в бледно-зеленый цвет, а символьные строки в нем – в темно-зеленый; для правого списка выберем сочетание цветов бледно-синий и темно-синий; сам диалог покрасим в очень бледно-желтый цвет. Заполнение списков выполним на этапе инициализации диалогового окна, занеся в левый список колонку чисел с их квадратами, а в правый – колонку чисел с их кубами.

В этом случае оконная функция диалогового окна примет такой вид:

BOOL CALLBACK DlgProc(HWND hwnd,UINT msg,WPARAM wParam,LPARAM lParam){

switch(msg){

HANDLE_MSG(hwnd,WM_INITDIALOG,DlgOnInitDialog);

HANDLE_MSG(hwnd,WM_CTLCOLORLISTBOX,DlgOnColorListBox);

HANDLE_MSG(hwnd,WM_CTLCOLORDLG,DlgOnColorDlg);

HANDLE_MSG(hwnd,WM_COMMAND,DlgOnCommand);

default:

return FALSE;

}

}

Процедуру заполнения списка содержимым (путем посылки в него в цикле сообщений LBADDSTRING) мы уже рассматривали. Приведем функции обработки сообщенийWMCTLCOLORDLGиWM_CTLCOLORLISTBOX:

HBRUSH DlgOnColorDlg(HWND,HDC,HWND,int){

/*Покрасим окно диалога в бледно-желтый цвет*/

return CreateSolidBrush(RGB(255,255,200));

}

HBRUSH DlgOnColorListBox(HWND hwndDlg,HDC hdc,HWND hwndCtl,int){

if(hwndCtl==GetDlgItem(hwndDlg,ID_LIST1)){//Если список 1

SetTextColor(hdc,RGB(0,128,0));//Покрасим текст зеленым

SetBkMode(hdc,TRANSPARENT);//Прозрачный фон

return CreateSolidBrush(RGB(180,255,180));/* Покрасим

список светло-зеленым*/

}

if(hwndCtl==GetDlgItem(hwndDlg,ID_LIST2)){//Если список 2

SetTextColor(hdc,RGB(0,0,128));//Покрасим текст синим

SetBkMode(hdc,TRANSPARENT);//Прозрачный фон

return CreateSolidBrush(RGB(180,180,255));/* Покрасим

список светло-синим*/

}

return FALSE;//Остальные элементы не обрабатываем

}

Воспользовавшись дескриптором контекста устройства hdc, поступающим в функцииDlgOnColorxxx, мы смогли назначить для каждого списка в отдельности цвет его строк и установить режим прозрачного фона (иначе строки изображались бы на белом фоне). Чтобы покрасить списки по-разному, в программе выполняется анализ параметраhwndCtl – дескриптора конкретного элемента. Разумеется, если оба списка требуется покрасить одинаково, в анализе этого дескриптора нет необходимости, и функция перекрашивания значительно упростится:

HBRUSH DlgOnColorListBox(HWND,HDC hdc,HWND,int){

SetTextColor(hdc,RGB(0,128,0));//Покрасим текст зеленым

SetBkMode(hdc,TRANSPARENT);//Прозрачный фон

return CreateSolidBrush(RGB(180,255,180));/*Покрасим

список светло-зеленым*/

}