Using Menus without Messages

How do you respond to a user's menu click? Via WM_COMMAND messages, right? Well, for pop-up menus, that isn't your only choice.

To show a popup menu, you can use TrackPopupMenu, of course. However, it is often not straightforward to respond to WM_COMMAND messages in this case. Luckily TrackPopupMenu has two flags to help in this case: TPM_NONOTIFY stops the menu from generating WM_COMMAND messages and TPM_RETURNCMD forces the call to return the menu ID selected.

Assume that you want to pop up a menu that contains the entries Red, Green, and Blue (with ID_RED, ID_GREEN, and ID_BLUE IDs). When the user selects a choice, you want to fill an edit box with the selection (represented by the MFC variable m_color). Here's the code:

  CMenu main,*pop;
  CRect r;
  CWnd *w=(CWnd *)lParam;
  w->GetWindowRect(&r);
  main.LoadMenu(IDR_COLORMENU);
  pop=main.GetSubMenu(0);
  switch (pop->TrackPopupMenu(TPM_NONOTIFY|TPM_RETURNCMD,r.left,r.top,this))
  {
  case ID_RED:
	  m_color="Red";
	  break;
  case ID_BLUE:
	  m_color="Blue";
	  break;
  case ID_GREEN:
	  m_color="Green";
	  break;
  default:
	  return 0;
  }
  UpdateData(FALSE);