2011-09-24 74 views
5

我有一個win32應用程序(C++),它有一個上下文菜單綁定到通知圖標上的右鍵單擊。菜單/子菜單項是在運行時動態創建和更改的。C++ win32動態菜單 - 哪個菜單項被選中

InsertMenu(hSettings, 0, MF_BYPOSITION | MF_POPUP | MF_STRING, (UINT_PTR) hDevices, L"Setting 1"); 
InsertMenu(hSettings, 1, MF_BYPOSITION | MF_POPUP | MF_STRING, (UINT_PTR) hChannels, L"Setting 2"); 

InsertMenu(hMainMenu, 0, MF_BYPOSITION | MF_POPUP | MF_STRING, (UINT_PTR) hSettings, L"Settings"); 
InsertMenu(hMainMenu, 1, MF_BYPOSITION | MF_STRING, IDM_EXIT, L"Exit"); 

在上面的代碼中,hDevices和hChannels是動態生成的子菜單。 動態菜單像這樣產生的:

InsertMenu(hDevices, i, style, IDM_DEVICE, L"Test 1"); 
    InsertMenu(hDevices, i, style, IDM_DEVICE, L"Test 2"); 
    InsertMenu(hDevices, i, style, IDM_DEVICE, L"Test 3"); 

是否有被點擊,而不必限定每個子菜單項它自己的ID(IDM_DEVICE在上面的代碼中),其項知道的方法嗎?在想要檢測到用戶點擊了子菜單IDM_DEVICE並且他點擊了該子菜單中的第一項(測試1)。

我想才達到這樣的事:

case WM_COMMAND: 
    wmId = LOWORD(wParam); 
    wmEvent = HIWORD(wParam); 
    // Parse the menu selections: 
    switch (wmId) 
    { 
     case IDM_DEVICE: // user clicked on Test 1 or Test 2 or Test 3 
      UINT index = getClickedMenuItem(); // get the index number of the clicked item (if you clicked on Test 1 it would be 0,..) 
          // change the style of the menu item with that index 
      break;   
    } 

回答

6

嘗試以下操作:

MENUINFO mi; 
memset(&mi, 0, sizeof(mi)); 
mi.cbSize = sizeof(mi); 
mi.fMask = MIM_STYLE; 
mi.dwStyle = MNS_NOTIFYBYPOS; 
SetMenuInfo(hDevices, &mi); 

現在你會得到的WM_MENUCOMMAND代替WM_COMMAND。菜單索引將在wParam和lParam中的菜單句柄中。請注意只吃已知菜單的信息,並將剩下的信息過濾到DefWindowProc。該代碼將與此類似:

case WM_MENUCOMMAND: 
    HMENU menu = (HMENU)lParam; 
    int idx = wParam; 
    if (menu == hDevices) 
    { 
     //Do useful things with device #idx 
    } 
    else 
     break; //Ensure that after that there is a DefWindowProc call 
+0

謝謝我一直在搜索一個樣本,找不到任何! – blejzz

0

你也可以使用TrackPopupMenuEx()與標誌TPM_RETURNCMD | TPM_NONOTIFY並獲得選擇的菜單項的id,而不必去通WM_MENUCOMMAND