Вход/Регистрация
Программирование для карманных компьютеров
вернуться

Волков Владимир

Шрифт:

20. Сдвинуться на один прямоугольник вправо на основной строке меню и взвести флажок Separator.

21. Сдвинуться на один прямоугольник вправо на основной строке меню и взвести флажки CheckButton, Group, Autosize, No wrap, Pressed и Bitmap. Свойство Bitmap Index должно получить нулевое значение.

22. Сдвинуться на один прямоугольник вправо на основной строке меню и взвести флажки CheckButton, Group, Autosize, No wrap и Bitmap. Свойство Bitmap Index должно получить значение 1.

23. Сдвинуться на один прямоугольник вправо на основной строке меню и взвести флажок Separator.

24. Подняться на один прямоугольник вверх. Для нового пункта меню свойство Caption должно получить значение UnGroup. Также нужно взвести флажки CheckButton, Autosize, No wrap и Pressed.

25. Результат должен получиться такой, как показано на рис. 4.11.

Рис. 4.11. Результат редактирования строки главного меню.

26. Кое-что может смутить разработчика. Картинки для кнопок еще не выбраны, а вместо них уже появились изображения кактусов. К тому же свойство Break ничего не изменило. Что ж, все это вполне поправимо. Свойство Break срабатывает только во время выполнения приложения, а с картинками мы сейчас разберемся.

27. Щелкнуть правой кнопкой мыши внутри дерева ресурсов на панели Resource View и выполнить команду контекстного меню Insert. В выведенном на экран окне нужно выбрать тип ресурса Bitmap и нажать кнопку New. В дереве ресурсов появится новая папка Bitmap, а в ней ресурс с идентификатором IDB_ BITMAP1. Если дважды щелкнуть по идентификатору ресурса, то в редакторе справа будет открыто для редактирования пустое изображение. Прежде всего нужно изменить размер изображения. Для этого достаточно просто перетащить мышью правый нижний угол изображения. После начала перетаскивания углового маркера на строке состояния среды будут отображаться цифры горизонтального и вертикального значений размера. Необходимо добиться размера 32x16, поскольку в одном изображении будут храниться картинки для двух кнопок, каждая размером 16x16. После получения картинки требуемого размера нужно на ней создать графическое изображение, показанное на рис. 4.12.

Рис. 4.12. Картинки с рисунком для двух кнопок.

28. Сохранить проект. Перейти на вкладку File View и открыть для редактирования файл menu.cpp. В этом файле нужно найти реализацию функции CreateRpCommandBar, после чего ее нужно изменить так, как показано в листинге 4.22. Листинг 4.22

mbi.nBmpId = 0;

mbi.cBmpImages = 0;

на:

mbi.nBmpId = IDB_BITMAP1;

mbi.cBmpImages = 2;

Этот фрагмент кода подключает изображение к меню и указывает, что в данном ресурсе хранятся изображения для двух кнопок. 29. Теперь нужно создать обработчики событий щелчка на том или ином пункте меню. Это будет сделано для одного пункта меню, который обозначен как File2. Ему автоматически присваивается идентификатор ID_FILE_FILE2. Это можно проверить, перейдя на вкладку Resource View и дважды щелкнув на соответствующей кнопке меню в редакторе ресурсов. В начале процедуры WndProc нужно объявить две переменных.

HMENU hMenu = NULL; MENUITEMINFO lpmii;

Это идентификатор меню (hMenu) и переменная, содержащая в своей структуре информацию об элементе меню (lpmii). Теперь в этой же процедуре в начало обработчика сообщения WM_COMMAND после строки switch (wmId) нужно добавить код, приведенный в листинге 4.23. Листинг 4.23

//если команда была сгенерирована щелчком на кнопке меню File2…

case ID_FILE_FILE2:

//…то извлечь указатель на конкретный пункт меню при помощи посылки

//сообщения SHCMBM_GETSUBMENU окну главного меню (g_hwndCB) с

//идентификатором пункта меню, на элемент которого мы хотим получить

//ссылку (ID_FILE)

hMenu = (HMENU)SendMessage(g_hwndCB, SHCMBM_GETSUBMENU, 0, ID_FILE);

//получив hMenu, мы извлекаем всю информацию об интересующем нас

//элементе меню по его идентификатору и помещаем ее в переменную lpmii:

GetMenuItemInfo(hMenu, ID_FILE_FILE2, false, &lpmii);

//проверяем поле fState структуры lpmii (то есть состояние

//соответствующего элемента меню:

if (lpmii.fState == 0)

//если состояние Unchecked, то устанавливаем флажок

CheckMenuItem(hMenu, ID_FILE_FILE2, MF_BYCOMMAND|MF_CHECKED);

else

//если состояние Checked, то сбрасываем флажок

CheckMenuItem(hMenu, ID_FILE_FILE2, MF_BYCOMMAND|MF_UNCHECKED);

break;

30. Завершить упражнение можно созданием контекстного меню для данной формы. Для этого нужно объявить переменную меню там же, где объявлена переменная меню g_hwndCB.

HMENUg_hmPopup;

31. Создать меню в обработчике сообщения WM_CREATE сразу после всех операций по созданию меню и добавить к этому меню несколько пунктов, как показано в листинге 4.24. Листинг 4.24

g_hmPopup = CreatePopupMenu;

AppendMenu(g_hmPopup,MF_STRING, 1000,TEXT(«pop 1»));

AppendMenu(g_hmPopup,MF_STRING, 1001, TEXT(«pop 2»));

AppendMenu(g_hmPopup,MF_STRING, 1002,TEXT(«pop 3»));

AppendMenu(g_hmPopup,MF_STRING|MF_MENUBARBREAK, 1003, TEXT(«pop 4»));

AppendMenu(g_hmPopup,MF_STRING|MF_CHECKED, 1004,TEXT(«pop 5»));

AppendMenu(g_hmPopup,MF_STRING, 1005, TEXT(«pop 6»));

32. Теперь нужно создать обработчик для вызова меню при щелчке правой кнопкой мыши, как показано в листинге 4.25. Листинг 4.25

case WM_LBUTTONDOWN:

{

WORD xPos = LOWORD(lParam); // horizontal position of the cursor

WORD yPos = HIWORD(lParam); // vertical position of the cursor

if (g_hmPopup){

TrackPopupMenuEx(g_hmPopup,0, xPos, yPos, hWnd, NULL);

}

}

break;

33. Запустить проект. Легко убедиться, что всплывающее меню работает так, как надо.

Стоит подробнее рассмотреть диалоговое окно создания и редактирования пункта меню. В этом окне три вкладки, на каждой из которых находятся элементы управления. Органы управления вкладки General перечислены в следующем списке.

? ID – идентификатор команды меню, по которому приложение будет обращаться к этой команде для обработки событий или манипуляций с данной кнопкой.

? Caption – название команды меню.

? Caption ID – идентификатор строкового ресурса, в котором хранится название команды меню.

? Pop-Up – установка этого флажка говорит о том, что данный пункт меню имеет подменю, которые будут выведены во всплывающем окне. В редакторе меню при выделении пункта меню с включенным свойством Pop-up над этим пунктом появляется прямоугольник, позволяющий редактировать всплывающее меню.

? Separator – установка этого флажка превращает данный пункт меню в разделитель.

? Shared New – выводит в строку меню кнопку New, предназначенную для создания нового пустого документа.

? Prompt – текст, предназначенный для автоматического показа в строке состояния, когда выбрана данная команда меню.

? Свойство Break имеет три состояния. Значение None указывает, что свойство не активно. Значение Column говорит о том, что данный пункт меню начинает следующий вертикальный столбец, а значение Bar указывает, что данный пункт меню начинает следующий вертикальный столбец, отделенный от предыдущего вертикальной линией.

В следующем списке рассматриваются органы управления, расположенные на вкладке Styles.

? Check Button – при установке данного флажка кнопка меню становится западающей. После первого щелчка мышью она переходит в нажатое состояние, после второго – возвращается в исходное состояние.

? Group – установка данного флажка позволяет создавать группу кнопок. Это имеет смысл, когда кнопки все имеют стиль Check Button. Тогда нажатие одной кнопки вызывает автоматическое отжатие другой кнопки в группе.

? Auto Size – автоматически меняет размер кнопки при изменении надписи.

? No wrap – установка флажка не позволяет переносить текст на другую строку.

? Pressed – нажатая кнопка при создании меню. Имеет смысл для кнопки со стилем Check Button.

? Grayed – кнопка будет окрашена в серый цвет и станет неактивна.

? Indeterminate – кнопка неопределенного стиля, активная, но серая.

? Hidden – скрытая кнопка.

? Highlighted – надпись кнопки подкрашена в контрастный цвет.

И наконец, в последнем списке рассматривается предназначение органов управления, расположенных на вкладке More Styles.

? Bitmap – кнопка вместо надписи несет на себе изображение.

? Bitmap index – уникальный индекс, идентифицирующий номер изображения в наборе изображений, подключенных к меню.

Однако меню не исчерпывает все потребности при создании набора команд. Гораздо большую гибкость дает элемент управления CommandBar.

CommandBar

Рассмотрение возможностей этого органа управления лучше начать с конкретного примера, который приведен в следующем разделе.

Упражнение 4.6

1. Создать простое приложение и сохранить его с именем CommandBar.

2. В окне Workspace перейти на вкладку ResourceView, открыть корневую папку Menu resources и в этой папке перейти в подкаталог Menubar. Существующее меню нужно отредактировать так, чтобы оно содержало команды Tools, File и Edit. Не надо добавлять дополнительные элементы в меню, создавать подменю и совершать прочие действия, которые уже рассматривались в предыдущем упражнении. Данное меню будет нужно только для демонстрации использования ресурса меню при помещении его в CommandBar.

3. Как и в прошлом упражнении, добавить к ресурсам изображение для кнопок.

4. Щелкнуть внутри дерева ресурсов правой клавишей мыши на папке Dialogs и в контекстном меню выполнить команду Insert Dialog. В папку будет добавлен еще один диалог с идентификатором IDD_DIALOG1. Теперь нужно перейти в правую часть окна, в редактор диалога. На панели Controls следует отыскать компонент Combo Box и поместить его на окно диалога.

5. Перейти в редактор кода, и в файле CommandBar.cpp добавить код, приведенный в листинге 4.26.

Листинг 4.26

//объявить хэндлеры для меню, компонентов CommandBar и Combo Box

HWNDg_hwndCombo, g_hwndMenu;

HMENUg_hmCB;

//объявление структуры для кнопок:

static TBBUTTON b_but1, b_but2, b_but3;

6. Теперь нужно перейти в процедуру WinProc и в ее начале объявить переменные, как показано в листинге 4.27. Листинг 4.27

int i;

RECT *lprc;

wchar_t *mstr[]={L"1", L"2", L"3", L"4"};

7. Удалить из обработчика сообщения WM_CREATE ранее сгенерированный код и ввести туда код, приведенный в листинге 4.28. Листинг 4.28

//Создаем CommandBar и помещаем его хэндлер в g_hwndCB

g_hwndCB = CommandBar_Create(g_hInst,hWnd, 500);

//Добавляем к списку изображений CommandBar (CB) наши рисунки

CommandBar_AddBitmap(g_hwndCB, g_hInst,IDB_BITMAP1, 2, 16, 16);

//Устанавливаем положение внизу окна

//Закомментируйте эту строку, и CB будет сверху

SendMessage (g_hwndCB, TB_SETSTYLE, 0, (LPARAM)(DWORD)CCS_BOTTOM);

//Добавляем в CB меню

CommandBar_InsertMenubar(g_hwndCB, g_hInst, IDM_MENU, 0);

//Добавляем в CB Combo Box

g_hwndCombo = CommandBar_InsertComboBox (g_hwndCB, g_hInst, 30,

WS_CHILD|WS_VISIBLE,IDC_COMBO1, 1);

//Задаем содержимое Combo Box

for (i=0;i<4;i++)

SendMessage (g_hwndCombo, CB_ADDSTRING, 0, (LPARAM)(LPCTSTR)mstr[i]);

//Устанавливаем текущую позицию, выбранную в Combo Box

SendMessage (g_hwndCombo, CB_SETCURSEL, (WPARAM)0, 0);

//Используя структуры свойств кнопок, устанавливаем их параметры

//и добавляем кнопки к CB

b_but1.iBitmap = 0;

b_but1.idCommand = 201;

b_but1.fsState = TBSTATE_ENABLED;

//Эта кнопка будет содержать в себе выпадающий список

b_but1.fsStyle =TBSTYLE_BUTTON | TBSTYLE_DROPDOWN;

b_but1.dwData = 0;

b_but1.iString = -1;

CommandBar_InsertButton (g_hwndCB, 2, &b_but1);

//Создаем выпадающий список для кнопки

g_hmCB = CreatePopupMenu;

AppendMenu(g_hmCB,MF_STRING, 1000,TEXT(«AI1»));

AppendMenu(g_hmCB,MF_STRING, 1001, TEXT(« AI2»));

//Следующие две кнопки будут зависеть друг от друга

b_but2.iBitmap = 1;

b_but2.idCommand = 202;

b_but2.fsState = TBSTATE_ENABLED;

b_but2.fsStyle = TBSTYLE_BUTTON|TBSTYLE_CHECKGROUP;

b_but2.dwData = 0;

b_but2.iString = -1;

CommandBar_InsertButton (g_hwndCB, 3, &b_but2);

b_but3.iBitmap = 0;

b_but3.idCommand = 203;

b_but3.fsState = TBSTATE_ENABLED;

b_but3.fsStyle = TBSTYLE_BUTTON|TBSTYLE_CHECKGROUP;

b_but3.dwData = 0;

b_but3.iString = -1;

CommandBar_InsertButton (g_hwndCB, 4, &b_but3);

break;

8. Запустить проект. Все должно работать, кроме выпадающего списка. Когда пользователь нажимает кнопку со стрелкой, щелчок на самой кнопке очень легко обработать в ветви WM_COMMAND, выловив идентификатор кнопки. Но вот как обработать щелчок на стрелке, чтобы появился выпадающий список? Теоретически, щелчок на этой стрелке должен генерировать константу TBN_DROPDOWN внутри поля lParam сообщения WM_NOTIFY, но, как выясняется, такой константы в этом поле нет. На самом деле в поле lParam помещается указатель на структуру LPTBNOTIFY, в которой есть поле hdr, в структуру которого входит поле code, в которое и помещается соответствующая константа. Значит, всего-то нужно выловить наличие константы в этом поле. Соответствующий код, располагающийся в процедуре WinProc, приведен в листинге 4.29. Листинг 4.29

case WM_NOTIFY:

//Ловим событие щелчка на стрелке к кнопке

if (((LPTBNOTIFY) lParam)->hdr.code == TBN_DROPDOWN)

{

//Находим углы кнопки, помещаем их в структуру lprc

SendMessage (g_hwndCB, TB_GETRECT, ((LPTBNOTIFY) lParam)->iItem, (LPARAM)(LPRECT)lprc);

//Находим место, где заканчивается окно, и начинается CB

i=CommandBar_Height(g_hwndCB);

//По найденным координатам выводим всплывающее меню так, чтобы оно

//в этой точке оказалось своим нижним правым углом (это задается

//константами TPM_RIGHTALIGN|TPM_BOTTOMALIGN

TrackPopupMenuEx(g_hmCB,TPM_RIGHTALIGN|TPM_BOTTOMALIGN, lprc->right, i, hWnd, NULL);

}

break;

  • Читать дальше
  • 1
  • ...
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • ...

Ебукер (ebooker) – онлайн-библиотека на русском языке. Книги доступны онлайн, без утомительной регистрации. Огромный выбор и удобный дизайн, позволяющий читать без проблем. Добавляйте сайт в закладки! Все произведения загружаются пользователями: если считаете, что ваши авторские права нарушены – используйте форму обратной связи.

Полезные ссылки

  • Моя полка

Контакты

  • chitat.ebooker@gmail.com

Подпишитесь на рассылку: