An String von Menu Item kommen?
-
Das Popup Menu (alles kurz zusammengefasst)...
HMENU hMenu = CreatePopupMenu();
InsertMenu (hMenu, 1, MF_STRING | MF_BYPOSITION | MF_OWNERDRAW, 888, L"Test Eintrag");
TrackPopupMenu(hMenu, TPM_RIGHTBUTTON | TPM_RETURNCMD, pt.x, pt.y, 0, hwnd, NULL);und dann die abfrage...
case WM_DRAWITEM:
LPDRAWITEMSTRUCT Item = (LPDRAWITEMSTRUCT)lParam;
GetMenuString((HMENU)Item->hwndItem, Item->itemID, lpBuff, 50, MF_BYCOMMAND);
MessageBox(hwnd,lpBuff,NULL,0);
-
OK, scheint wohl das richtige Handle laut DRAWITEMSTRUCT zu sein.
Und wie ist
lpBuff
deklariert und initialisiert?Üblicherweise würde man es so programmieren:
TCHAR buff[50] = { 0 }; GetMenuString((HMENU)Item->hwndItem, Item->itemID, buff, sizeof(buff)/sizeof(buff[0]), MF_BYCOMMAND); MessageBox(hwnd, buff, NULL, MB_OK);
-
Genau so habe ich es auch initialisiert.
-
Mich hat nur der Prefix
lp
(long pointer) verwundert.Aber so langsam bin ich jetzt auch überfragt.
Klappt denn überhaupt das Auslesen, z.B.
GetMenuString((HMENU)Item->hwndItem, 0, buff, sizeof(buff)/sizeof(buff[0]), MF_BYPOSITION); // 1. Menüeintrag
?
-
Nein, klappt nicht.
-
Hast du denn mal den Wert von
hwndItem
jetzt überprüft, ob der dem Rückgabewert vonCreatePopupMenu
entspricht?Das sollte doch alles mittels Debuggen innerhalb von ein paar Minuten erledigt sein...
Edit: Und hast du beim Zeichnen denn auch den Typ abgefragt (
item->CtlType == ODT_MENU
)?
-
Ich würde als erstes mal probieren das direkt nach
InsertMenu
zum Laufen zu bekommen. Mit dem korrekten Handle. Und mich dann von dort aus weiterhanteln.
-
@Th69 ja hab geprüfte auf ODT_MENU und der Handle ist auch der selbe.
-
@Mike85Dev sagte in An String von Menu Item kommen?:
InsertMenu (hMenu, 1, MF_STRING | MF_BYPOSITION | MF_OWNERDRAW, 888, L"Test Eintrag");
Das Ding gibt nen
BOOL
zurück. Könnte leicht sein dass da0
zurückkommt.Versuch's mal mit
0
bzw.-1
füruPosition
.
Ansonsten:GetLastError
nach dem Aufruf prüfen.
-
Sieh Dir einmal die Parameterbeschreibung für lpNewItem aus der Funktion InsertMenu an und was MF_OWNERDRAW dort bewirkt.
Das OWNERDRAW-Flag erst nach dem Aufruf von InsertMenu setzen, dann klappt es auch. ;o)
Oder besser gleich InsertMenuItem benutzen.
-
Beim Aufruf von InsertMenu macht es keinen Sinn, sowohl `MF_STRING' als auch 'MF_OWNERDRAW' anzugeben.
InsertMenu (hMenu, 1, MF_BYPOSITION | MF_OWNERDRAW, 888, L"Test Eintrag");
Und dann braucht auch bei
WM_DRAWITEM
nicht extraGetMenuString
aufgerufen werden, denn inItem->itemData
steht dann der Zeiger auf den übergebenen Text drin.s.a. Creating Owner-Drawn Menu Items
Ergo: Wichtig, wenn etwas nicht funktioniert: Doku lesen und vernünftig debuggen.
PS: Erzeugst du denn (laut deinem Code) einfach ein neues Popup-Menu mit diesem einem Eintrag?! Warum verwendest du dann nicht AppendMenu?
-
@Th69 sagte in An String von Menu Item kommen?:
Beim Aufruf von InsertMenu macht es keinen Sinn, sowohl `MF_STRING' als auch 'MF_OWNERDRAW' anzugeben.
MF_STRING
ist eh nur symbolische Kosmetik, weil Wert gleich 0.Und dann braucht auch bei
WM_DRAWITEM
nicht extraGetMenuString
aufgerufen werden (auch wenn immer noch nicht geklärt ist, warum es nicht funktioniert?!), denn inItem->itemData
steht dann der Zeiger auf den übergebenen Text drin).Weil
GetMenuString
keinen Zeiger auf eine Zeichenkette findet, denn (wie Du richtig erkannt hast) der OP hat den Zeiger mit seinem Aufruf vonInsertMenu
plus ´MF_OWNERDRAW´ indwItemData
abgelegt und nicht indwTypeData
.
MENUITEMINFOW structureDie alten Menüfunktionen sind nur noch Wrapper der neuen Menüfunktionen wie InsertMenuItem oder Get-/SetMenuItemInfo.
(Edit: Dies ist nur eine Annahme meinerseits)Daher mein Rat besser gleich InserMenuItem zu benutzen.
LG
Greenhorn
-
Ja, ist ja (jetzt) auch logisch, daß dann kein String-Text ausgelesen werden kann, da ja nicht zwangsläufig ein String bei
MF_OWNERDRAW
übergeben werden muß, sondern es kann ja auch eine beliebige Datenstruktur o.ä. sein.
-
Doch das geht. Hab gemerkt das der String sich in Item->itemData versteckt hat. Ich musste nicht mal was beim Menü erstellen ändern. Danke für eure Hilfe ️
-
@Mike85Dev sagte in An String von Menu Item kommen?:
Doch das geht. Hab gemerkt das der String sich in Item->itemData versteckt hat. Ich musste nicht mal was beim Menü erstellen ändern. Danke für eure Hilfe ️
Das geht nur, so lange garantiert ist dass der Speicherbereich in dem der String steht nicht freigegeben wird so lange das Menu existiert.
Probier das selbe mal mitstd::wstring text = L"Test Eintrag"; InsertMenu (hMenu, 0, MF_STRING | MF_BYPOSITION | MF_OWNERDRAW, 888, text.c_str());
dann siehst du was ich meine.
-
Und ich meinte bei
@Th69 sagte in An String von Menu Item kommen?:Ja, ist ja (jetzt) auch logisch, daß dann kein String-Text ausgelesen werden kann, da ja nicht zwangsläufig ein String bei
MF_OWNERDRAW
übergeben werden muß, sondern es kann ja auch eine beliebige Datenstruktur o.ä. sein.explizit das Auslesen mittels der
GetMenuString
-Funktion.