Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2003.12.26;
Скачать: CL | DM;

Вниз

Owner Draw Menu Item   Найти похожие ветки 

 
Dima_dvp ©   (2003-11-01 01:25) [0]

Уважаемые мастера, возникла необходимость вывести меню с иконками(у каждого пункта своя уникальная). Для этого по видимому следует использывать "ручную" прорисовку пунктов меню.
Не могу разобраться к какому окну всё-таки должны приходить сообщения WM_MEASUREITEM, WM_DRAWITEM если меню является Popup.

Код:


TLinkedItem = record
id: DWORD;
lpcPath: PChar;
lpcTitle: PChar;
hMenu: HMENU;
next: PLinkedItem;
end;

//**************************************************************
//ФУНКЦИЯ, СОХРАНЯЮЩАЯ НЕКИЙ СПИСОК В МЕНЮ
function TLinkedList.SaveToMenu(const hMenu: HMENU; const defaultIcon: HICON): DWORD;
var
Cursor: PLinkedItem;
MII: tagMenuItemInfo;
begin
//Устанавливаем курсор в начало
Cursor := FFirst;

//Очищаем меню
//КСТАТИ ТОЖЕ ВОПРОС КАК ЛУЧШЕ ОЧИСТИТЬ МЕНЮ?
while DeleteMenu(hMenu, 0, MF_BYPOSITION) do;
//Пока не достигнут конец спсика
while Cursor <> nil do begin
//Добавляем пункт
ZeroMemory(@MII, SizeOf(MII));
MII.cbSize := SizeOf(MII);
MII.fMask := MIIM_DATA or MIIM_TYPE or MIIM_ID or MIIM_BITMAP;
MII.fType := MFT_STRING;
MII.wID := Cursor^.id;
MII.dwItemData := Cursor^.id;
MII.dwTypeData := Cursor^.lpcTitle;
MII.hbmpItem := HBITMAP(HBMMENU_CALLBACK);
//MII.cch := lstrlen(Cursor^.lpcTitle);

if not InsertMenuItem(hMenu, 0, True, MII) then begin
//Result := GetLastError();
Result := 20;
Exit;
end;

Cursor := Cursor^.next;
//Устанавливаем иконку у этого пункта меню
end;

Result := 0;
end;

//**************************************************************
//ВИДИМО ОБРАБОТКА МЕНЮ ДОЛЖНА ВЫГЛЯДЕТЬ КАК-ТО ТАК, НО В КАКОЙ WndProc?
//Отрисовка пункта меню
WM_DRAWITEM: begin
//Если пришло от меню
if wParam = 0 then begin
DrawItem(PDRAWITEMSTRUCT(lParam));
Result := Integer(True);
end;
end;
//.......
WM_MEASUREITEM: begin
//Если пришло от меню
if wParam = 0 then begin
MeasureItem(PMEASUREITEMSTRUCT(lParam));
Result := Integer(True);
end;
end;

//*************************************************************
//А ВОТ ТАК СОЗДАВАЛОСЬ СОБСТВЕННО МЕНЮ
//Создаём меню
progMenu := CreatePopupMenu;



Подскажите пожалуста...
Заранее благодарен


 
Dima_dvp ©   (2003-11-01 02:01) [1]

Да кстати если это важно, то отмечу что меню выводиться при клике по иконке в трее...


 
Nick Denry ©   (2003-11-01 12:45) [2]

WM_Syscdicon: {


 
Nick Denry ©   (2003-11-01 12:46) [3]

var
menu_pstr : TpaintStruct;
menu,submenu : HMENU;

{menu pens&brushes ghtabrc "M"


 
Nick Denry ©   (2003-11-01 12:47) [4]

{


 
Nick Denry ©   (2003-11-01 12:48) [5]

куриные кубики Магги - просто как раз, два, три... ;-)


 
Nick Denry ©   (2003-11-01 13:06) [6]

Заранеее пожалуиста... :))


 
Dima_dvp ©   (2003-11-01 13:12) [7]

Спасибо..., но зачем орать-то, можно было просто сказать....


 
Nick Denry ©   (2003-11-01 13:26) [8]

:)


 
Dima_dvp ©   (2003-11-01 13:38) [9]

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

SubMenu := GetSubMenu(menu,0);

а никак не

SubMenu := CreatePopupMenu;

я прав? Но мне совсем не нужно главное меню... Или с этим придётся смириться?


 
Dima_dvp ©   (2003-11-01 13:45) [10]


//Добавляем пункт
ZeroMemory(@MII, SizeOf(MII));
MII.cbSize := SizeOf(MII);
MII.fMask := MIIM_DATA or MIIM_TYPE or MIIM_ID or MIIM_BITMAP;
MII.fType := MFT_STRING;
MII.wID := Cursor^.id; //неважно что такое Cursor
MII.dwItemData := Cursor^.id;
MII.dwTypeData := Cursor^.lpcTitle;
//включение нижеследуюшей строки приводит к ошибка при вставке пункта меню
MII.hbmpItem := HBITMAP(HBMMENU_CALLBACK);
//MII.cch := lstrlen(Cursor^.lpcTitle);

if not InsertMenuItem(hMenu, 0, True, MII) then begin
//Result := GetLastError();
Result := 20;
Exit;
end;


Что делать, чтобы меню было OwnerDraw и странно, что OwnerDraw устанавливается для каждого пункта меню отдельно.... или может этот пункт должен быть SubMenu обязательно и тогда будет OwnerDraw только вложенное мменю????
Разъясните плиз...


 
Nick Denry ©   (2003-11-01 13:46) [11]

[9]Нет. ТЫ ен прав - я в своем коде просто выделяю тот участок меню из главного, который мне нужен. (мое меню - из ресурса). Не важно как было созданно меню - оно в любом случае получает хендл - hMEnu:)

HMENU CreateMenu(VOID)

Parameters

This function has no parameters.

********************************
или

HMENU CreatePopupMenu(VOID)


Parameters

This function has no parameters
.
***************************************
и даже

HMENU LoadMenu(

HINSTANCE hInstance, // handle of application instance
LPCTSTR lpMenuName // menu name string or menu-resource identifier
);

дают одинаковый результат...


 
Dima_dvp ©   (2003-11-01 13:50) [12]

Но чем определяется окно, к которому придёт сообщение WM_DRAWITEM??? Тем, в чьей WindProc будет вызов TrackPopupMenu? Вообще не понятно это, а тем более когда меню выводиться по щелчку в трее...


 
Nick Denry ©   (2003-11-01 13:51) [13]

2>[10]
Настоятельно рекомендую, если меню не изменяется динамически - грузить его из ресурса.
Ownerdraw я действительно устанавливал для каждого пункта отдельно - но использовал при этом функцию
Функция SetMenuItemInfo модуль Windows
Группа ссылок: Меню

Описание:
function SetMenuItemInfo(p1: HMENU; p2: UINT; p3: BOOL; const p4: TMenuItemInfo): BOOL;

Используется для получения информации о пункте меню.

Параметры:
p1: дискриптор меню, которое содержит пункт меню
p2: индентификатор (fByPosition=FALSE) или позиция (fByPosition=TRUE) пункта меню, для которого устанавливаем информацию
p3: Определяет содержание параметра p2

p4: указатель на структуру TMenuItemInfo, в которой содержится устанавливаемая информация

Возвращаемые значения
Если успешно то не ноль.
Если функция терпит неудачу - ноль. Чтобы получить расширенную информацию об ошибке, вызовите функцию GetLastError.

См. также: GetMenuItemInfo

Функция находится в файле user32.dll


 
Nick Denry ©   (2003-11-01 13:55) [14]

2>[12] - не понял вопроса - что не понятного?

Рекомендую : русская справка по WinApi http://www.soobcha.ru/rushelp


 
Dima_dvp ©   (2003-11-01 14:19) [15]

Справочку щас посмотрю..
А непонятно следкщее: Чем определяется окно, котому посылаются эти сообщения: С главным меню всё понятно потому что оно привязано к окну а всплывающие меню я же могу показать как реакцию на клик в любом окне.. Вот тут и возникает вопрос куда придут сообщения...
И ещё GetLastError возвращает ошибку 87 если я в MenuItemInfo ставлю MII.hbmpItem := HBITMAP(HBMMENU_CALLBACK); Впринципе в SDK этого поля вообще нету, а вот в книге у меня оно описано.
Меню заполняется только динамически и поэтому ресурсы использывать нельзя.
Привидите пример как вы используете SetMenuItemInfo в частности параметр MenuItemInfo
Спасибо за помощь


 
Dima_dvp ©   (2003-11-01 14:35) [16]

Кажется разобрался, спсибо за помощь


 
andre ©   (2003-11-01 14:39) [17]

А SetMenuItemBitMaps никак не пойдёт?


 
Nick Denry ©   (2003-11-01 16:33) [18]

2>[15]

А непонятно следкщее: Чем определяется окно, котому посылаются эти сообщения: С главным меню всё понятно потому что оно привязано к окну а всплывающие меню я же могу показать как реакцию на клик в любом окне.. Вот тут и возникает вопрос куда придут сообщения...

Окно определяется окном, а вот сообщеня придут в любом случае в оконную процедуру обработки сообщений...



Страницы: 1 вся ветка

Текущий архив: 2003.12.26;
Скачать: CL | DM;

Наверх




Память: 0.51 MB
Время: 0.011 c
1-86392
Шустрый
2003-12-15 22:01
2003.12.26
Программное нажате ENTER


3-86266
volser
2003-11-29 13:33
2003.12.26
SQL InterBase?


4-86600
Serhio
2003-10-31 16:10
2003.12.26
Убить процесс


14-86501
Карелин Артем
2003-12-04 14:33
2003.12.26
Что может висеть на 7000 порту?


3-86265
Nikolai_S
2003-12-03 15:15
2003.12.26
ADO & SQL Server2000