[PATCH] user32: Don't depend on HMENU being valid for popup menus
Andrew Eikum
aeikum at codeweavers.com
Tue May 6 09:28:14 CDT 2014
Now we use raw struct pointers internally instead of HMENUs. This lets
an application call DestroyMenu() without invalidating a menu that is
in use internally.
---
I couldn't think of a good way to split this patch, as we lose the HMENU
refcounting that some of the tests depend on by passing the raw
pointers.
dlls/user32/menu.c | 756 +++++++++++++++++++++++------------------------
dlls/user32/tests/menu.c | 4 +-
2 files changed, 375 insertions(+), 385 deletions(-)
diff --git a/dlls/user32/menu.c b/dlls/user32/menu.c
index ab3f73b..4b091b0 100644
--- a/dlls/user32/menu.c
+++ b/dlls/user32/menu.c
@@ -67,13 +67,15 @@ WINE_DECLARE_DEBUG_CHANNEL(accel);
#define MM_SETMENUHANDLE (WM_USER + 0)
#define MM_GETMENUHANDLE (WM_USER + 1)
+typedef struct _POPUPMENU POPUPMENU, *LPPOPUPMENU;
+
/* Menu item structure */
typedef struct {
/* ----------- MENUITEMINFO Stuff ----------- */
UINT fType; /* Item type. */
UINT fState; /* Item state. */
UINT_PTR wID; /* Item id. */
- HMENU hSubMenu; /* Pop-up menu. */
+ POPUPMENU *submenu;
HBITMAP hCheckBit; /* Bitmap when checked. */
HBITMAP hUnCheckBit; /* Bitmap when unchecked. */
LPWSTR text; /* Item text. */
@@ -88,7 +90,7 @@ typedef struct {
} MENUITEM;
/* Popup menu structure */
-typedef struct {
+struct _POPUPMENU {
struct user_object obj;
WORD wFlags; /* Menu flags (MF_POPUP, MF_SYSMENU) */
WORD Width; /* Width of the whole menu */
@@ -102,6 +104,7 @@ typedef struct {
BOOL bScrolling; /* Scroll arrows are active */
UINT nScrollPos; /* Current scroll position */
UINT nTotalHeight; /* Total height of menu items inside menu */
+ LONG refcount;
/* ------------ MENUINFO members ------ */
DWORD dwStyle; /* Extended menu style */
UINT cyMax; /* max height of the whole menu, 0 is screen height */
@@ -110,7 +113,7 @@ typedef struct {
DWORD dwMenuData; /* application defined value */
HMENU hSysMenuOwner; /* Handle to the dummy sys menu holder */
WORD textOffset; /* Offset of text when items have both bitmaps and text */
-} POPUPMENU, *LPPOPUPMENU;
+};
/* internal flags for menu tracking */
@@ -121,8 +124,8 @@ typedef struct {
typedef struct
{
UINT trackFlags;
- HMENU hCurrentMenu; /* current submenu (can be equal to hTopMenu)*/
- HMENU hTopMenu; /* initial menu */
+ POPUPMENU *current_menu;
+ POPUPMENU *top_menu;
HWND hOwnerWnd; /* where notifications are sent */
POINT pt;
} MTRACKER;
@@ -178,7 +181,7 @@ static UINT ODitemheight; /* default owner drawn item height */
/* Use global popup window because there's no way 2 menus can
* be tracked at the same time. */
static HWND top_popup;
-static HMENU top_popup_hmenu;
+static POPUPMENU *top_popup_menu;
/* Flag set by EndMenu() to force an exit from menu tracking */
static BOOL fEndMenu = FALSE;
@@ -186,6 +189,7 @@ static BOOL fEndMenu = FALSE;
DWORD WINAPI DrawMenuBarTemp(HWND hwnd, HDC hDC, LPRECT lprect, HMENU hMenu, HFONT hFont);
static BOOL SetMenuItemInfo_common( MENUITEM *, const MENUITEMINFOW *, BOOL);
+static BOOL MENU_ReleaseMenu( POPUPMENU *lppop );
/*********************************************************************
* menu class descriptor
@@ -200,6 +204,10 @@ const struct builtin_class_descr MENU_builtin_class =
(HBRUSH)(COLOR_MENU+1) /* brush */
};
+static HMENU MENU_GetHandle(POPUPMENU *menu)
+{
+ return menu ? menu->obj.handle : NULL;
+}
/***********************************************************************
* debug_print_menuitem
@@ -229,8 +237,8 @@ static void do_debug_print_menuitem(const char *prefix, const MENUITEM *mp,
if (mp) {
UINT flags = mp->fType;
TRACE( "{ ID=0x%lx", mp->wID);
- if ( mp->hSubMenu)
- TRACE( ", Sub=%p", mp->hSubMenu);
+ if ( mp->submenu)
+ TRACE( ", Sub=%p", MENU_GetHandle(mp->submenu));
if (flags) {
int count = 0;
TRACE( ", fType=");
@@ -533,16 +541,11 @@ static void MENU_InitSysMenuPopup( HMENU hmenu, DWORD style, DWORD clsStyle )
/******************************************************************************
- *
- * UINT MENU_GetStartOfNextColumn(
- * HMENU hMenu )
- *
+ * MENU_GetStartOfNextColumn
*****************************************************************************/
-static UINT MENU_GetStartOfNextColumn(
- HMENU hMenu )
+static UINT MENU_GetStartOfNextColumn( POPUPMENU *menu )
{
- POPUPMENU *menu = MENU_GetMenu(hMenu);
UINT i;
if(!menu)
@@ -562,16 +565,11 @@ static UINT MENU_GetStartOfNextColumn(
/******************************************************************************
- *
- * UINT MENU_GetStartOfPrevColumn(
- * HMENU hMenu )
- *
+ * MENU_GetStartOfPrevColumn
*****************************************************************************/
-static UINT MENU_GetStartOfPrevColumn(
- HMENU hMenu )
+static UINT MENU_GetStartOfPrevColumn( POPUPMENU *menu )
{
- POPUPMENU *menu = MENU_GetMenu(hMenu);
UINT i;
if( !menu )
@@ -604,17 +602,18 @@ static UINT MENU_GetStartOfPrevColumn(
/***********************************************************************
* MENU_FindItem
*
- * Find a menu item. Return a pointer on the item, and modifies *hmenu
+ * Find a menu item. Return a pointer on the item, and modifies *pmenu
* in case the item was in a sub-menu.
*/
-static MENUITEM *MENU_FindItem( HMENU *hmenu, UINT *nPos, UINT wFlags )
+static MENUITEM *MENU_FindItem( POPUPMENU **pmenu, UINT *nPos, UINT wFlags )
{
- POPUPMENU *menu;
+ POPUPMENU *menu = *pmenu;
MENUITEM *fallback = NULL;
UINT fallback_pos = 0;
UINT i;
- if ((*hmenu == (HMENU)0xffff) || (!(menu = MENU_GetMenu(*hmenu)))) return NULL;
+ if (!menu) return NULL;
+
if (wFlags & MF_BYPOSITION)
{
if (*nPos >= menu->nItems) return NULL;
@@ -627,11 +626,11 @@ static MENUITEM *MENU_FindItem( HMENU *hmenu, UINT *nPos, UINT wFlags )
{
if (item->fType & MF_POPUP)
{
- HMENU hsubmenu = item->hSubMenu;
- MENUITEM *subitem = MENU_FindItem( &hsubmenu, nPos, wFlags );
+ POPUPMENU *submenu = item->submenu;
+ MENUITEM *subitem = MENU_FindItem( &submenu, nPos, wFlags );
if (subitem)
{
- *hmenu = hsubmenu;
+ *pmenu = submenu;
return subitem;
}
else if (item->wID == *nPos)
@@ -659,28 +658,27 @@ static MENUITEM *MENU_FindItem( HMENU *hmenu, UINT *nPos, UINT wFlags )
* MENU_FindSubMenu
*
* Find a Sub menu. Return the position of the submenu, and modifies
- * *hmenu in case it is found in another sub-menu.
+ * *pmenu in case it is found in another sub-menu.
* If the submenu cannot be found, NO_SELECTED_ITEM is returned.
*/
-static UINT MENU_FindSubMenu( HMENU *hmenu, HMENU hSubTarget )
+static UINT MENU_FindSubMenu( POPUPMENU **pmenu, POPUPMENU *subTarget )
{
- POPUPMENU *menu;
+ POPUPMENU *menu = *pmenu;
UINT i;
MENUITEM *item;
- if (((*hmenu)==(HMENU)0xffff) ||
- (!(menu = MENU_GetMenu(*hmenu))))
+ if (!menu)
return NO_SELECTED_ITEM;
item = menu->items;
for (i = 0; i < menu->nItems; i++, item++) {
if(!(item->fType & MF_POPUP)) continue;
- if (item->hSubMenu == hSubTarget) {
+ if (item->submenu == subTarget) {
return i;
}
else {
- HMENU hsubmenu = item->hSubMenu;
- UINT pos = MENU_FindSubMenu( &hsubmenu, hSubTarget );
+ POPUPMENU *submenu = item->submenu;
+ UINT pos = MENU_FindSubMenu( &submenu, subTarget );
if (pos != NO_SELECTED_ITEM) {
- *hmenu = hsubmenu;
+ *pmenu = submenu;
return pos;
}
}
@@ -757,16 +755,15 @@ static MENUITEM *MENU_FindItemByCoords( const POPUPMENU *menu,
* Find the menu item selected by a key press.
* Return item id, -1 if none, -2 if we should close the menu.
*/
-static UINT MENU_FindItemByKey( HWND hwndOwner, HMENU hmenu,
+static UINT MENU_FindItemByKey( HWND hwndOwner, POPUPMENU *menu,
WCHAR key, BOOL forceMenuChar )
{
- TRACE("\tlooking for '%c' (0x%02x) in [%p]\n", (char)key, key, hmenu );
+ TRACE("\tlooking for '%c' (0x%02x) in [%p]\n", (char)key, key, menu );
- if (!IsMenu( hmenu )) hmenu = GetSubMenu( get_win_sys_menu(hwndOwner), 0);
+ if (!menu) menu = MENU_GetMenu(GetSubMenu( get_win_sys_menu(hwndOwner), 0));
- if (hmenu)
+ if (menu)
{
- POPUPMENU *menu = MENU_GetMenu( hmenu );
MENUITEM *item = menu->items;
LRESULT menuchar;
@@ -792,7 +789,7 @@ static UINT MENU_FindItemByKey( HWND hwndOwner, HMENU hmenu,
}
}
menuchar = SendMessageW( hwndOwner, WM_MENUCHAR,
- MAKEWPARAM( key, menu->wFlags ), (LPARAM)hmenu );
+ MAKEWPARAM( key, menu->wFlags ), (LPARAM)MENU_GetHandle(menu) );
if (HIWORD(menuchar) == MNC_EXECUTE) return LOWORD(menuchar);
if (HIWORD(menuchar) == MNC_CLOSE) return (UINT)(-2);
}
@@ -867,7 +864,7 @@ static void MENU_GetBitmapItemSize( MENUITEM *lpitem, SIZE *size,
* Draw a bitmap item.
*/
static void MENU_DrawBitmapItem( HDC hdc, MENUITEM *lpitem, const RECT *rect,
- HMENU hmenu, HWND hwndOwner, UINT odaction, BOOL menuBar)
+ POPUPMENU *menu, HWND hwndOwner, UINT odaction, BOOL menuBar)
{
BITMAP bm;
DWORD rop;
@@ -934,7 +931,7 @@ static void MENU_DrawBitmapItem( HDC hdc, MENUITEM *lpitem, const RECT *rect,
drawItem.itemState |= (lpitem->fState & MF_DISABLED)?ODS_DISABLED:0;
drawItem.itemState |= (lpitem->fState & MF_GRAYED)?ODS_GRAYED|ODS_DISABLED:0;
drawItem.itemState |= (lpitem->fState & MF_HILITE)?ODS_SELECTED:0;
- drawItem.hwndItem = (HWND)hmenu;
+ drawItem.hwndItem = (HWND)MENU_GetHandle(menu);
drawItem.hDC = hdc;
drawItem.itemData = lpitem->dwItemData;
drawItem.rcItem = *rect;
@@ -1396,14 +1393,13 @@ static void draw_popup_arrow( HDC hdc, RECT rect, UINT arrow_bitmap_width,
*
* Draw a single menu item.
*/
-static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc, MENUITEM *lpitem,
+static void MENU_DrawMenuItem( HWND hwnd, POPUPMENU *menu, HWND hwndOwner, HDC hdc, MENUITEM *lpitem,
UINT height, BOOL menuBar, UINT odaction )
{
RECT rect;
BOOL flat_menu = FALSE;
int bkgnd;
UINT arrow_bitmap_width = 0, arrow_bitmap_height = 0;
- POPUPMENU *menu = MENU_GetMenu(hmenu);
RECT bmprc;
debug_print_menuitem("MENU_DrawMenuItem: ", lpitem, "");
@@ -1451,7 +1447,7 @@ static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc,
TRACE("rect=%s\n", wine_dbgstr_rect( &lpitem->rect));
rect = lpitem->rect;
- MENU_AdjustMenuItemRect(MENU_GetMenu(hmenu), &rect);
+ MENU_AdjustMenuItemRect(menu, &rect);
if (lpitem->fType & MF_OWNERDRAW)
{
@@ -1475,7 +1471,7 @@ static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc,
if (lpitem->fState & MF_GRAYED) dis.itemState |= ODS_GRAYED|ODS_DISABLED;
if (lpitem->fState & MF_HILITE) dis.itemState |= ODS_SELECTED;
dis.itemAction = odaction; /* ODA_DRAWENTIRE | ODA_SELECT | ODA_FOCUS; */
- dis.hwndItem = (HWND)hmenu;
+ dis.hwndItem = (HWND)MENU_GetHandle(menu);
dis.hDC = hdc;
dis.rcItem = rect;
TRACE("Ownerdraw: owner=%p itemID=%d, itemState=%d, itemAction=%d, "
@@ -1637,7 +1633,7 @@ static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc,
POINT origorg;
/* some applications make this assumption on the DC's origin */
SetViewportOrgEx( hdc, rect.left, rect.top, &origorg);
- MENU_DrawBitmapItem(hdc, lpitem, &bmprc, hmenu, hwndOwner,
+ MENU_DrawBitmapItem(hdc, lpitem, &bmprc, menu, hwndOwner,
odaction, FALSE);
SetViewportOrgEx( hdc, origorg.x, origorg.y, NULL);
}
@@ -1655,7 +1651,7 @@ static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc,
POINT origorg;
SetViewportOrgEx( hdc, rect.left, rect.top, &origorg);
- MENU_DrawBitmapItem( hdc, lpitem, &bmprc, hmenu, hwndOwner,
+ MENU_DrawBitmapItem( hdc, lpitem, &bmprc, menu, hwndOwner,
odaction, menuBar);
SetViewportOrgEx( hdc, origorg.x, origorg.y, NULL);
}
@@ -1781,7 +1777,7 @@ static void MENU_DrawPopupMenu( HWND hwnd, HDC hdc, HMENU hmenu )
item = menu->items;
for( u = menu->nItems; u > 0; u--, item++)
- MENU_DrawMenuItem( hwnd, hmenu, menu->hwndOwner, hdc,
+ MENU_DrawMenuItem( hwnd, menu, menu->hwndOwner, hdc,
item, menu->Height, FALSE, ODA_DRAWENTIRE );
}
/* draw scroll arrows */
@@ -1821,14 +1817,13 @@ UINT MENU_DrawMenuBar( HDC hDC, LPRECT lprect, HWND hwnd )
*
* Popup menu initialization before WM_ENTERMENULOOP.
*/
-static BOOL MENU_InitPopup( HWND hwndOwner, HMENU hmenu, UINT flags )
+static BOOL MENU_InitPopup( HWND hwndOwner, POPUPMENU *menu, UINT flags )
{
- POPUPMENU *menu;
DWORD ex_style = 0;
- TRACE("owner=%p hmenu=%p\n", hwndOwner, hmenu);
+ TRACE("owner=%p menu=%p\n", hwndOwner, menu);
- if (!(menu = MENU_GetMenu( hmenu ))) return FALSE;
+ if (!menu) return FALSE;
/* store the owner for DrawItem */
if (!IsWindow( hwndOwner ))
@@ -1845,7 +1840,7 @@ static BOOL MENU_InitPopup( HWND hwndOwner, HMENU hmenu, UINT flags )
menu->hWnd = CreateWindowExW( ex_style, (LPCWSTR)POPUPMENU_CLASS_ATOM, NULL,
WS_POPUP, 0, 0, 0, 0,
hwndOwner, 0, (HINSTANCE)GetWindowLongPtrW(hwndOwner, GWLP_HINSTANCE),
- (LPVOID)hmenu );
+ (LPVOID)MENU_GetHandle(menu) );
if( !menu->hWnd ) return FALSE;
return TRUE;
}
@@ -1856,21 +1851,23 @@ static BOOL MENU_InitPopup( HWND hwndOwner, HMENU hmenu, UINT flags )
*
* Display a popup menu.
*/
-static BOOL MENU_ShowPopup( HWND hwndOwner, HMENU hmenu, UINT id, UINT flags,
+static BOOL MENU_ShowPopup( HWND hwndOwner, POPUPMENU *menu, UINT id, UINT flags,
INT x, INT y, INT xanchor, INT yanchor )
{
- POPUPMENU *menu;
INT width, height;
POINT pt;
HMONITOR monitor;
MONITORINFO info;
- TRACE("owner=%p hmenu=%p id=0x%04x x=0x%04x y=0x%04x xa=0x%04x ya=0x%04x\n",
- hwndOwner, hmenu, id, x, y, xanchor, yanchor);
+ TRACE("owner=%p menu=%p id=0x%04x x=0x%04x y=0x%04x xa=0x%04x ya=0x%04x\n",
+ hwndOwner, menu, id, x, y, xanchor, yanchor);
- if (!(menu = MENU_GetMenu( hmenu ))) return FALSE;
+ if (!menu) return FALSE;
if (menu->FocusedItem != NO_SELECTED_ITEM)
{
+ ERR("focused: %u, nitms: 0x%x\n",
+ menu->FocusedItem,
+ menu->nItems);
menu->items[menu->FocusedItem].fState &= ~(MF_HILITE|MF_MOUSESELECT);
menu->FocusedItem = NO_SELECTED_ITEM;
}
@@ -1921,7 +1918,7 @@ static BOOL MENU_ShowPopup( HWND hwndOwner, HMENU hmenu, UINT id, UINT flags,
if (!top_popup) {
top_popup = menu->hWnd;
- top_popup_hmenu = hmenu;
+ top_popup_menu = menu;
}
/* Display the window */
@@ -1976,15 +1973,13 @@ MENU_EnsureMenuItemVisible(LPPOPUPMENU lppop, UINT wIndex, HDC hdc)
/***********************************************************************
* MENU_SelectItem
*/
-static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
- BOOL sendMenuSelect, HMENU topmenu )
+static void MENU_SelectItem( HWND hwndOwner, POPUPMENU *lppop, UINT wIndex,
+ BOOL sendMenuSelect, POPUPMENU *topmenu )
{
- LPPOPUPMENU lppop;
HDC hdc;
- TRACE("owner=%p menu=%p index=0x%04x select=0x%04x\n", hwndOwner, hmenu, wIndex, sendMenuSelect);
+ TRACE("owner=%p menu=%p index=0x%04x select=0x%04x\n", hwndOwner, lppop, wIndex, sendMenuSelect);
- lppop = MENU_GetMenu( hmenu );
if ((!lppop) || (!lppop->nItems) || (!lppop->hWnd)) return;
if (lppop->FocusedItem == wIndex) return;
@@ -1992,7 +1987,7 @@ static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
else hdc = GetDCEx( lppop->hWnd, 0, DCX_CACHE | DCX_WINDOW);
if (!top_popup) {
top_popup = lppop->hWnd;
- top_popup_hmenu = hmenu;
+ top_popup_menu = lppop;
}
SelectObject( hdc, get_menu_font(FALSE));
@@ -2001,7 +1996,7 @@ static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
if (lppop->FocusedItem != NO_SELECTED_ITEM)
{
lppop->items[lppop->FocusedItem].fState &= ~(MF_HILITE|MF_MOUSESELECT);
- MENU_DrawMenuItem(lppop->hWnd, hmenu, hwndOwner, hdc,&lppop->items[lppop->FocusedItem],
+ MENU_DrawMenuItem(lppop->hWnd, lppop, hwndOwner, hdc,&lppop->items[lppop->FocusedItem],
lppop->Height, !(lppop->wFlags & MF_POPUP),
ODA_SELECT );
}
@@ -2013,7 +2008,7 @@ static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
if(!(lppop->items[wIndex].fType & MF_SEPARATOR)) {
lppop->items[wIndex].fState |= MF_HILITE;
MENU_EnsureMenuItemVisible(lppop, wIndex, hdc);
- MENU_DrawMenuItem( lppop->hWnd, hmenu, hwndOwner, hdc,
+ MENU_DrawMenuItem( lppop->hWnd, lppop, hwndOwner, hdc,
&lppop->items[wIndex], lppop->Height,
!(lppop->wFlags & MF_POPUP), ODA_SELECT );
}
@@ -2023,18 +2018,17 @@ static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
SendMessageW( hwndOwner, WM_MENUSELECT,
MAKEWPARAM(ip->fType & MF_POPUP ? wIndex: ip->wID,
ip->fType | ip->fState |
- (lppop->wFlags & MF_SYSMENU)), (LPARAM)hmenu);
+ (lppop->wFlags & MF_SYSMENU)), (LPARAM)MENU_GetHandle(lppop));
}
}
else if (sendMenuSelect) {
if(topmenu){
int pos;
- if((pos=MENU_FindSubMenu(&topmenu, hmenu))!=NO_SELECTED_ITEM){
- POPUPMENU *ptm = MENU_GetMenu( topmenu );
- MENUITEM *ip = &ptm->items[pos];
+ if((pos=MENU_FindSubMenu(&topmenu, lppop))!=NO_SELECTED_ITEM){
+ MENUITEM *ip = &topmenu->items[pos];
SendMessageW( hwndOwner, WM_MENUSELECT, MAKEWPARAM(pos,
ip->fType | ip->fState |
- (ptm->wFlags & MF_SYSMENU)), (LPARAM)topmenu);
+ (topmenu->wFlags & MF_SYSMENU)), (LPARAM)topmenu);
}
}
}
@@ -2049,14 +2043,12 @@ static void MENU_SelectItem( HWND hwndOwner, HMENU hmenu, UINT wIndex,
* If there is no selection then it should select the last item if
* offset is ITEM_PREV or the first item if offset is ITEM_NEXT.
*/
-static void MENU_MoveSelection( HWND hwndOwner, HMENU hmenu, INT offset )
+static void MENU_MoveSelection( HWND hwndOwner, POPUPMENU *menu, INT offset )
{
INT i;
- POPUPMENU *menu;
- TRACE("hwnd=%p hmenu=%p off=0x%04x\n", hwndOwner, hmenu, offset);
+ TRACE("hwnd=%p menu=%p off=0x%04x\n", hwndOwner, menu, offset);
- menu = MENU_GetMenu( hmenu );
if ((!menu) || (!menu->items)) return;
if ( menu->FocusedItem != NO_SELECTED_ITEM )
@@ -2066,7 +2058,7 @@ static void MENU_MoveSelection( HWND hwndOwner, HMENU hmenu, INT offset )
; i += offset)
if (!(menu->items[i].fType & MF_SEPARATOR))
{
- MENU_SelectItem( hwndOwner, hmenu, i, TRUE, 0 );
+ MENU_SelectItem( hwndOwner, menu, i, TRUE, 0 );
return;
}
}
@@ -2075,7 +2067,7 @@ static void MENU_MoveSelection( HWND hwndOwner, HMENU hmenu, INT offset )
i >= 0 && i < menu->nItems ; i += offset)
if (!(menu->items[i].fType & MF_SEPARATOR))
{
- MENU_SelectItem( hwndOwner, hmenu, i, TRUE, 0 );
+ MENU_SelectItem( hwndOwner, menu, i, TRUE, 0 );
return;
}
}
@@ -2100,12 +2092,9 @@ static MENUITEM *MENU_InsertItem( HMENU hMenu, UINT pos, UINT flags )
if (pos > menu->nItems)
pos = menu->nItems;
} else {
- if (!MENU_FindItem( &hMenu, &pos, flags ))
+ MENUITEM *item = MENU_FindItem( &menu, &pos, flags );
+ if (!item)
pos = menu->nItems;
- else {
- if (!(menu = MENU_GetMenu( hMenu )))
- return NULL;
- }
}
/* Make sure that MDI system buttons stay on the right side.
@@ -2246,21 +2235,18 @@ static LPCSTR MENUEX_ParseResource( LPCSTR res, HMENU hMenu)
/***********************************************************************
* MENU_GetSubPopup
*
- * Return the handle of the selected sub-popup menu (if any).
+ * Return the selected sub-popup menu (if any).
*/
-static HMENU MENU_GetSubPopup( HMENU hmenu )
+static POPUPMENU *MENU_GetSubPopup( POPUPMENU *menu )
{
- POPUPMENU *menu;
MENUITEM *item;
- menu = MENU_GetMenu( hmenu );
-
- if ((!menu) || (menu->FocusedItem == NO_SELECTED_ITEM)) return 0;
+ if ((!menu) || (menu->FocusedItem == NO_SELECTED_ITEM)) return NULL;
item = &menu->items[menu->FocusedItem];
if ((item->fType & MF_POPUP) && (item->fState & MF_MOUSESELECT))
- return item->hSubMenu;
- return 0;
+ return item->submenu;
+ return NULL;
}
@@ -2269,16 +2255,14 @@ static HMENU MENU_GetSubPopup( HMENU hmenu )
*
* Hide the sub-popup menus of this menu.
*/
-static void MENU_HideSubPopups( HWND hwndOwner, HMENU hmenu,
+static void MENU_HideSubPopups( HWND hwndOwner, POPUPMENU *menu,
BOOL sendMenuSelect, UINT wFlags )
{
- POPUPMENU *menu = MENU_GetMenu( hmenu );
- TRACE("owner=%p hmenu=%p 0x%04x\n", hwndOwner, hmenu, sendMenuSelect);
+ TRACE("owner=%p menu=%p 0x%04x\n", hwndOwner, menu, sendMenuSelect);
if (menu && top_popup)
{
- HMENU hsubmenu;
POPUPMENU *submenu;
MENUITEM *item;
@@ -2288,17 +2272,17 @@ static void MENU_HideSubPopups( HWND hwndOwner, HMENU hmenu,
if (!(item->fType & MF_POPUP) ||
!(item->fState & MF_MOUSESELECT)) return;
item->fState &= ~MF_MOUSESELECT;
- hsubmenu = item->hSubMenu;
+ submenu = item->submenu;
} else return;
- if (!(submenu = MENU_GetMenu( hsubmenu ))) return;
- MENU_HideSubPopups( hwndOwner, hsubmenu, FALSE, wFlags );
- MENU_SelectItem( hwndOwner, hsubmenu, NO_SELECTED_ITEM, sendMenuSelect, 0 );
+ if (!submenu) return;
+ MENU_HideSubPopups( hwndOwner, submenu, FALSE, wFlags );
+ MENU_SelectItem( hwndOwner, submenu, NO_SELECTED_ITEM, sendMenuSelect, 0 );
DestroyWindow( submenu->hWnd );
submenu->hWnd = 0;
if (!(wFlags & TPM_NONOTIFY))
- SendMessageW( hwndOwner, WM_UNINITMENUPOPUP, (WPARAM)hsubmenu,
+ SendMessageW( hwndOwner, WM_UNINITMENUPOPUP, (WPARAM)MENU_GetHandle(submenu),
MAKELPARAM(0, IS_SYSTEM_MENU(submenu)) );
}
}
@@ -2308,32 +2292,31 @@ static void MENU_HideSubPopups( HWND hwndOwner, HMENU hmenu,
* MENU_ShowSubPopup
*
* Display the sub-menu of the selected item of this menu.
- * Return the handle of the submenu, or hmenu if no submenu to display.
+ * Return the handle of the submenu, or menu if no submenu to display.
*/
-static HMENU MENU_ShowSubPopup( HWND hwndOwner, HMENU hmenu,
+static POPUPMENU *MENU_ShowSubPopup( HWND hwndOwner, POPUPMENU *menu,
BOOL selectFirst, UINT wFlags )
{
RECT rect;
- POPUPMENU *menu;
MENUITEM *item;
HDC hdc;
- TRACE("owner=%p hmenu=%p 0x%04x\n", hwndOwner, hmenu, selectFirst);
+ TRACE("owner=%p menu=%p 0x%04x\n", hwndOwner, menu, selectFirst);
- if (!(menu = MENU_GetMenu( hmenu ))) return hmenu;
+ if (!menu) return NULL;
- if (menu->FocusedItem == NO_SELECTED_ITEM) return hmenu;
+ if (menu->FocusedItem == NO_SELECTED_ITEM) return menu;
item = &menu->items[menu->FocusedItem];
if (!(item->fType & MF_POPUP) || (item->fState & (MF_GRAYED | MF_DISABLED)))
- return hmenu;
+ return menu;
/* message must be sent before using item,
because nearly everything may be changed by the application ! */
/* Send WM_INITMENUPOPUP message only if TPM_NONOTIFY flag is not specified */
if (!(wFlags & TPM_NONOTIFY))
- SendMessageW( hwndOwner, WM_INITMENUPOPUP, (WPARAM)item->hSubMenu,
+ SendMessageW( hwndOwner, WM_INITMENUPOPUP, (WPARAM)MENU_GetHandle(item->submenu),
MAKELPARAM( menu->FocusedItem, IS_SYSTEM_MENU(menu) ));
item = &menu->items[menu->FocusedItem];
@@ -2348,7 +2331,7 @@ static HMENU MENU_ShowSubPopup( HWND hwndOwner, HMENU hmenu,
SelectObject( hdc, get_menu_font(FALSE));
item->fState |= MF_HILITE;
- MENU_DrawMenuItem( menu->hWnd, hmenu, hwndOwner, hdc, item, menu->Height, !(menu->wFlags & MF_POPUP), ODA_DRAWENTIRE );
+ MENU_DrawMenuItem( menu->hWnd, menu, hwndOwner, hdc, item, menu->Height, !(menu->wFlags & MF_POPUP), ODA_DRAWENTIRE );
ReleaseDC( menu->hWnd, hdc );
}
if (!item->rect.top && !item->rect.left && !item->rect.bottom && !item->rect.right)
@@ -2358,7 +2341,7 @@ static HMENU MENU_ShowSubPopup( HWND hwndOwner, HMENU hmenu,
if (IS_SYSTEM_MENU(menu))
{
- MENU_InitSysMenuPopup(item->hSubMenu,
+ MENU_InitSysMenuPopup(MENU_GetHandle(item->submenu),
GetWindowLongW( menu->hWnd, GWL_STYLE ),
GetClassLongW( menu->hWnd, GCL_STYLE));
@@ -2403,13 +2386,13 @@ static HMENU MENU_ShowSubPopup( HWND hwndOwner, HMENU hmenu,
/* use default alignment for submenus */
wFlags &= ~(TPM_CENTERALIGN | TPM_RIGHTALIGN | TPM_VCENTERALIGN | TPM_BOTTOMALIGN);
- MENU_InitPopup( hwndOwner, item->hSubMenu, wFlags );
+ MENU_InitPopup( hwndOwner, item->submenu, wFlags );
- MENU_ShowPopup( hwndOwner, item->hSubMenu, menu->FocusedItem, wFlags,
+ MENU_ShowPopup( hwndOwner, item->submenu, menu->FocusedItem, wFlags,
rect.left, rect.top, rect.right, rect.bottom );
if (selectFirst)
- MENU_MoveSelection( hwndOwner, item->hSubMenu, ITEM_NEXT );
- return item->hSubMenu;
+ MENU_MoveSelection( hwndOwner, item->submenu, ITEM_NEXT );
+ return item->submenu;
}
@@ -2431,9 +2414,7 @@ HWND MENU_IsMenuActive(void)
*/
void MENU_EndMenu( HWND hwnd )
{
- POPUPMENU *menu;
- menu = top_popup_hmenu ? MENU_GetMenu( top_popup_hmenu ) : NULL;
- if (menu && (hwnd == menu->hWnd || hwnd == menu->hwndOwner)) EndMenu();
+ if (top_popup_menu && (hwnd == top_popup_menu->hWnd || hwnd == top_popup_menu->hwndOwner)) EndMenu();
}
/***********************************************************************
@@ -2441,29 +2422,28 @@ void MENU_EndMenu( HWND hwnd )
*
* Walks menu chain trying to find a menu pt maps to.
*/
-static HMENU MENU_PtMenu( HMENU hMenu, POINT pt )
+static POPUPMENU *MENU_PtMenu( POPUPMENU *menu, POINT pt )
{
- POPUPMENU *menu = MENU_GetMenu( hMenu );
UINT item = menu->FocusedItem;
- HMENU ret;
+ POPUPMENU *ret;
/* try subpopup first (if any) */
ret = (item != NO_SELECTED_ITEM &&
(menu->items[item].fType & MF_POPUP) &&
(menu->items[item].fState & MF_MOUSESELECT))
- ? MENU_PtMenu(menu->items[item].hSubMenu, pt) : 0;
+ ? MENU_PtMenu(menu->items[item].submenu, pt) : 0;
if (!ret) /* check the current window (avoiding WM_HITTEST) */
{
INT ht = NC_HandleNCHitTest( menu->hWnd, pt );
if( menu->wFlags & MF_POPUP )
{
- if (ht != HTNOWHERE && ht != HTERROR) ret = hMenu;
+ if (ht != HTNOWHERE && ht != HTERROR) ret = menu;
}
else if (ht == HTSYSMENU)
- ret = get_win_sys_menu( menu->hWnd );
+ ret = MENU_GetMenu(get_win_sys_menu( menu->hWnd ));
else if (ht == HTMENU)
- ret = GetMenu( menu->hWnd );
+ ret = MENU_GetMenu(GetMenu( menu->hWnd ));
}
return ret;
}
@@ -2478,19 +2458,18 @@ static HMENU MENU_PtMenu( HMENU hMenu, POINT pt )
* sending unwanted message.
*
*/
-static INT MENU_ExecFocusedItem( MTRACKER* pmt, HMENU hMenu, UINT wFlags )
+static INT MENU_ExecFocusedItem( MTRACKER* pmt, POPUPMENU *menu, UINT wFlags )
{
MENUITEM *item;
- POPUPMENU *menu = MENU_GetMenu( hMenu );
- TRACE("%p hmenu=%p\n", pmt, hMenu);
+ TRACE("%p menu=%p\n", pmt, menu);
if (!menu || !menu->nItems ||
(menu->FocusedItem == NO_SELECTED_ITEM)) return -1;
item = &menu->items[menu->FocusedItem];
- TRACE("hMenu %p wID %08lx hSubMenu %p fType %04x\n", hMenu, item->wID, item->hSubMenu, item->fType);
+ TRACE("menu %p wID %08lx submenu %p fType %04x\n", menu, item->wID, item->submenu, item->fType);
if (!(item->fType & MF_POPUP))
{
@@ -2505,12 +2484,11 @@ static INT MENU_ExecFocusedItem( MTRACKER* pmt, HMENU hMenu, UINT wFlags )
MAKELPARAM((INT16)pmt->pt.x, (INT16)pmt->pt.y) );
else
{
- POPUPMENU *topmenu = MENU_GetMenu( pmt->hTopMenu );
- DWORD dwStyle = menu->dwStyle | (topmenu ? topmenu->dwStyle : 0);
+ DWORD dwStyle = menu->dwStyle | (pmt->top_menu ? pmt->top_menu->dwStyle : 0);
if (dwStyle & MNS_NOTIFYBYPOS)
PostMessageW( pmt->hOwnerWnd, WM_MENUCOMMAND, menu->FocusedItem,
- (LPARAM)hMenu);
+ (LPARAM)MENU_GetHandle(menu));
else
PostMessageW( pmt->hOwnerWnd, WM_COMMAND, item->wID, 0 );
}
@@ -2520,7 +2498,7 @@ static INT MENU_ExecFocusedItem( MTRACKER* pmt, HMENU hMenu, UINT wFlags )
}
else
{
- pmt->hCurrentMenu = MENU_ShowSubPopup(pmt->hOwnerWnd, hMenu, TRUE, wFlags);
+ pmt->current_menu = MENU_ShowSubPopup(pmt->hOwnerWnd, menu, TRUE, wFlags);
return -2;
}
@@ -2532,23 +2510,20 @@ static INT MENU_ExecFocusedItem( MTRACKER* pmt, HMENU hMenu, UINT wFlags )
*
* Helper function for menu navigation routines.
*/
-static void MENU_SwitchTracking( MTRACKER* pmt, HMENU hPtMenu, UINT id, UINT wFlags )
+static void MENU_SwitchTracking( MTRACKER* pmt, POPUPMENU *ptmenu, UINT id, UINT wFlags )
{
- POPUPMENU *ptmenu = MENU_GetMenu( hPtMenu );
- POPUPMENU *topmenu = MENU_GetMenu( pmt->hTopMenu );
+ TRACE("%p ptmenu=%p 0x%04x\n", pmt, ptmenu, id);
- TRACE("%p hmenu=%p 0x%04x\n", pmt, hPtMenu, id);
-
- if( pmt->hTopMenu != hPtMenu &&
- !((ptmenu->wFlags | topmenu->wFlags) & MF_POPUP) )
+ if( pmt->top_menu != ptmenu &&
+ !((ptmenu->wFlags | pmt->top_menu->wFlags) & MF_POPUP) )
{
- /* both are top level menus (system and menu-bar) */
- MENU_HideSubPopups( pmt->hOwnerWnd, pmt->hTopMenu, FALSE, wFlags );
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hTopMenu, NO_SELECTED_ITEM, FALSE, 0 );
- pmt->hTopMenu = hPtMenu;
+ /* both are top level menus (system and menu-bar) */
+ MENU_HideSubPopups( pmt->hOwnerWnd, pmt->top_menu, FALSE, wFlags );
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->top_menu, NO_SELECTED_ITEM, FALSE, 0 );
+ pmt->top_menu = ptmenu;
}
- else MENU_HideSubPopups( pmt->hOwnerWnd, hPtMenu, FALSE, wFlags );
- MENU_SelectItem( pmt->hOwnerWnd, hPtMenu, id, TRUE, 0 );
+ else MENU_HideSubPopups( pmt->hOwnerWnd, ptmenu, FALSE, wFlags );
+ MENU_SelectItem( pmt->hOwnerWnd, ptmenu, id, TRUE, 0 );
}
@@ -2557,14 +2532,13 @@ static void MENU_SwitchTracking( MTRACKER* pmt, HMENU hPtMenu, UINT id, UINT wFl
*
* Return TRUE if we can go on with menu tracking.
*/
-static BOOL MENU_ButtonDown( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
+static BOOL MENU_ButtonDown( MTRACKER* pmt, POPUPMENU *ptmenu, UINT wFlags )
{
- TRACE("%p hPtMenu=%p\n", pmt, hPtMenu);
+ TRACE("%p ptmenu=%p\n", pmt, ptmenu);
- if (hPtMenu)
+ if (ptmenu)
{
UINT id = 0;
- POPUPMENU *ptmenu = MENU_GetMenu( hPtMenu );
MENUITEM *item;
if( IS_SYSTEM_MENU(ptmenu) )
@@ -2575,12 +2549,12 @@ static BOOL MENU_ButtonDown( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
if( item )
{
if( ptmenu->FocusedItem != id )
- MENU_SwitchTracking( pmt, hPtMenu, id, wFlags );
+ MENU_SwitchTracking( pmt, ptmenu, id, wFlags );
/* If the popup menu is not already "popped" */
if(!(item->fState & MF_MOUSESELECT ))
{
- pmt->hCurrentMenu = MENU_ShowSubPopup( pmt->hOwnerWnd, hPtMenu, FALSE, wFlags );
+ pmt->current_menu = MENU_ShowSubPopup( pmt->hOwnerWnd, ptmenu, FALSE, wFlags );
}
return TRUE;
@@ -2598,14 +2572,13 @@ static BOOL MENU_ButtonDown( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
* A -1 return value indicates that we go on with menu tracking.
*
*/
-static INT MENU_ButtonUp( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags)
+static INT MENU_ButtonUp( MTRACKER* pmt, POPUPMENU *ptmenu, UINT wFlags)
{
- TRACE("%p hmenu=%p\n", pmt, hPtMenu);
+ TRACE("%p menu=%p\n", pmt, ptmenu);
- if (hPtMenu)
+ if (ptmenu)
{
UINT id = 0;
- POPUPMENU *ptmenu = MENU_GetMenu( hPtMenu );
MENUITEM *item;
if( IS_SYSTEM_MENU(ptmenu) )
@@ -2619,7 +2592,7 @@ static INT MENU_ButtonUp( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags)
if( !(item->fType & MF_POPUP) )
{
- INT executedMenuId = MENU_ExecFocusedItem( pmt, hPtMenu, wFlags);
+ INT executedMenuId = MENU_ExecFocusedItem( pmt, ptmenu, wFlags);
if (executedMenuId == -1 || executedMenuId == -2) return -1;
return executedMenuId;
}
@@ -2627,7 +2600,7 @@ static INT MENU_ButtonUp( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags)
/* If we are dealing with the top-level menu */
/* and this is a click on an already "popped" item: */
/* Stop the menu tracking and close the opened submenus */
- if((pmt->hTopMenu == hPtMenu) && ptmenu->bTimeToHide)
+ if(pmt->top_menu == ptmenu && ptmenu->bTimeToHide)
return 0;
}
ptmenu->bTimeToHide = TRUE;
@@ -2641,14 +2614,12 @@ static INT MENU_ButtonUp( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags)
*
* Return TRUE if we can go on with menu tracking.
*/
-static BOOL MENU_MouseMove( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
+static BOOL MENU_MouseMove( MTRACKER* pmt, POPUPMENU *ptmenu, UINT wFlags )
{
UINT id = NO_SELECTED_ITEM;
- POPUPMENU *ptmenu = NULL;
- if( hPtMenu )
+ if( ptmenu )
{
- ptmenu = MENU_GetMenu( hPtMenu );
if( IS_SYSTEM_MENU(ptmenu) )
id = 0;
else
@@ -2657,14 +2628,14 @@ static BOOL MENU_MouseMove( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
if( id == NO_SELECTED_ITEM )
{
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hCurrentMenu,
- NO_SELECTED_ITEM, TRUE, pmt->hTopMenu);
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->current_menu,
+ NO_SELECTED_ITEM, TRUE, pmt->top_menu);
}
else if( ptmenu->FocusedItem != id )
{
- MENU_SwitchTracking( pmt, hPtMenu, id, wFlags );
- pmt->hCurrentMenu = MENU_ShowSubPopup(pmt->hOwnerWnd, hPtMenu, FALSE, wFlags);
+ MENU_SwitchTracking( pmt, ptmenu, id, wFlags );
+ pmt->current_menu = MENU_ShowSubPopup(pmt->hOwnerWnd, ptmenu, FALSE, wFlags);
}
return TRUE;
}
@@ -2677,35 +2648,34 @@ static BOOL MENU_MouseMove( MTRACKER* pmt, HMENU hPtMenu, UINT wFlags )
*/
static LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk, UINT wFlags )
{
- POPUPMENU *menu = MENU_GetMenu( pmt->hTopMenu );
BOOL atEnd = FALSE;
/* When skipping left, we need to do something special after the
first menu. */
- if (vk == VK_LEFT && menu->FocusedItem == 0)
+ if (vk == VK_LEFT && pmt->top_menu->FocusedItem == 0)
{
atEnd = TRUE;
}
/* When skipping right, for the non-system menu, we need to
handle the last non-special menu item (ie skip any window
icons such as MDI maximize, restore or close) */
- else if ((vk == VK_RIGHT) && !IS_SYSTEM_MENU(menu))
+ else if ((vk == VK_RIGHT) && !IS_SYSTEM_MENU(pmt->top_menu))
{
- UINT i = menu->FocusedItem + 1;
- while (i < menu->nItems) {
- if ((menu->items[i].wID >= SC_SIZE &&
- menu->items[i].wID <= SC_RESTORE)) {
+ UINT i = pmt->top_menu->FocusedItem + 1;
+ while (i < pmt->top_menu->nItems) {
+ if ((pmt->top_menu->items[i].wID >= SC_SIZE &&
+ pmt->top_menu->items[i].wID <= SC_RESTORE)) {
i++;
} else break;
}
- if (i == menu->nItems) {
+ if (i == pmt->top_menu->nItems) {
atEnd = TRUE;
}
}
/* When skipping right, we need to cater for the system menu */
- else if ((vk == VK_RIGHT) && IS_SYSTEM_MENU(menu))
+ else if ((vk == VK_RIGHT) && IS_SYSTEM_MENU(pmt->top_menu))
{
- if (menu->FocusedItem == (menu->nItems - 1)) {
+ if (pmt->top_menu->FocusedItem == (pmt->top_menu->nItems - 1)) {
atEnd = TRUE;
}
}
@@ -2717,19 +2687,19 @@ static LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk, UINT wFlags )
HWND hNewWnd;
UINT id = 0;
- next_menu.hmenuIn = (IS_SYSTEM_MENU(menu)) ? GetSubMenu(pmt->hTopMenu,0) : pmt->hTopMenu;
+ next_menu.hmenuIn = (IS_SYSTEM_MENU(pmt->top_menu)) ? GetSubMenu(MENU_GetHandle(pmt->top_menu), 0) : MENU_GetHandle(pmt->top_menu);
next_menu.hmenuNext = 0;
next_menu.hwndNext = 0;
SendMessageW( pmt->hOwnerWnd, WM_NEXTMENU, vk, (LPARAM)&next_menu );
TRACE("%p [%p] -> %p [%p]\n",
- pmt->hCurrentMenu, pmt->hOwnerWnd, next_menu.hmenuNext, next_menu.hwndNext );
+ pmt->current_menu, pmt->hOwnerWnd, next_menu.hmenuNext, next_menu.hwndNext );
if (!next_menu.hmenuNext || !next_menu.hwndNext)
{
DWORD style = GetWindowLongW( pmt->hOwnerWnd, GWL_STYLE );
hNewWnd = pmt->hOwnerWnd;
- if( IS_SYSTEM_MENU(menu) )
+ if( IS_SYSTEM_MENU(pmt->top_menu) )
{
/* switch to the menu bar */
@@ -2737,7 +2707,7 @@ static LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk, UINT wFlags )
if( vk == VK_LEFT )
{
- menu = MENU_GetMenu( hNewMenu );
+ POPUPMENU *menu = MENU_GetMenu( hNewMenu );
id = menu->nItems - 1;
/* Skip backwards over any system predefined icons,
@@ -2781,12 +2751,12 @@ static LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk, UINT wFlags )
else return FALSE;
}
- if( hNewMenu != pmt->hTopMenu )
+ if( pmt->top_menu && hNewMenu != MENU_GetHandle(pmt->top_menu) )
{
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hTopMenu, NO_SELECTED_ITEM,
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->top_menu, NO_SELECTED_ITEM,
FALSE, 0 );
- if( pmt->hCurrentMenu != pmt->hTopMenu )
- MENU_HideSubPopups( pmt->hOwnerWnd, pmt->hTopMenu, FALSE, wFlags );
+ if( pmt->current_menu != pmt->top_menu )
+ MENU_HideSubPopups( pmt->hOwnerWnd, pmt->top_menu, FALSE, wFlags );
}
if( hNewWnd != pmt->hOwnerWnd )
@@ -2795,8 +2765,8 @@ static LRESULT MENU_DoNextMenu( MTRACKER* pmt, UINT vk, UINT wFlags )
set_capture_window( pmt->hOwnerWnd, GUI_INMENUMODE, NULL );
}
- pmt->hTopMenu = pmt->hCurrentMenu = hNewMenu; /* all subpopups are hidden */
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hTopMenu, id, TRUE, 0 );
+ pmt->top_menu = pmt->current_menu = MENU_GetMenu(hNewMenu); /* all subpopups are hidden */
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->top_menu, id, TRUE, 0 );
return TRUE;
}
@@ -2850,25 +2820,23 @@ static BOOL MENU_KeyEscape(MTRACKER* pmt, UINT wFlags)
{
BOOL bEndMenu = TRUE;
- if (pmt->hCurrentMenu != pmt->hTopMenu)
+ if (pmt->current_menu != pmt->top_menu)
{
- POPUPMENU *menu = MENU_GetMenu(pmt->hCurrentMenu);
-
- if (menu->wFlags & MF_POPUP)
+ if (pmt->current_menu->wFlags & MF_POPUP)
{
- HMENU hmenutmp, hmenuprev;
+ POPUPMENU *menutmp, *menuprev;
- hmenuprev = hmenutmp = pmt->hTopMenu;
+ menuprev = menutmp = pmt->top_menu;
/* close topmost popup */
- while (hmenutmp != pmt->hCurrentMenu)
+ while (menutmp != pmt->current_menu)
{
- hmenuprev = hmenutmp;
- hmenutmp = MENU_GetSubPopup( hmenuprev );
+ menuprev = menutmp;
+ menutmp = MENU_GetSubPopup( menuprev );
}
- MENU_HideSubPopups( pmt->hOwnerWnd, hmenuprev, TRUE, wFlags );
- pmt->hCurrentMenu = hmenuprev;
+ MENU_HideSubPopups( pmt->hOwnerWnd, menuprev, TRUE, wFlags );
+ pmt->current_menu = menuprev;
bEndMenu = FALSE;
}
}
@@ -2883,47 +2851,45 @@ static BOOL MENU_KeyEscape(MTRACKER* pmt, UINT wFlags)
*/
static void MENU_KeyLeft( MTRACKER* pmt, UINT wFlags )
{
- POPUPMENU *menu;
- HMENU hmenutmp, hmenuprev;
+ POPUPMENU *menu, *menutmp, *menuprev;
UINT prevcol;
- hmenuprev = hmenutmp = pmt->hTopMenu;
- menu = MENU_GetMenu( hmenutmp );
+ menu = menuprev = menutmp = pmt->top_menu;
/* Try to move 1 column left (if possible) */
- if( (prevcol = MENU_GetStartOfPrevColumn( pmt->hCurrentMenu )) !=
+ if( (prevcol = MENU_GetStartOfPrevColumn( pmt->current_menu )) !=
NO_SELECTED_ITEM ) {
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hCurrentMenu,
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->current_menu,
prevcol, TRUE, 0 );
return;
}
/* close topmost popup */
- while (hmenutmp != pmt->hCurrentMenu)
+ while (menutmp != pmt->current_menu)
{
- hmenuprev = hmenutmp;
- hmenutmp = MENU_GetSubPopup( hmenuprev );
+ menuprev = menutmp;
+ menutmp = MENU_GetSubPopup( menuprev );
}
- MENU_HideSubPopups( pmt->hOwnerWnd, hmenuprev, TRUE, wFlags );
- pmt->hCurrentMenu = hmenuprev;
+ MENU_HideSubPopups( pmt->hOwnerWnd, menuprev, TRUE, wFlags );
+ pmt->current_menu = menuprev;
- if ( (hmenuprev == pmt->hTopMenu) && !(menu->wFlags & MF_POPUP) )
+ if ( (menuprev == pmt->top_menu) && !(menu->wFlags & MF_POPUP) )
{
/* move menu bar selection if no more popups are left */
if( !MENU_DoNextMenu( pmt, VK_LEFT, wFlags ) )
- MENU_MoveSelection( pmt->hOwnerWnd, pmt->hTopMenu, ITEM_PREV );
+ MENU_MoveSelection( pmt->hOwnerWnd, pmt->top_menu, ITEM_PREV );
- if ( hmenuprev != hmenutmp || pmt->trackFlags & TF_SUSPENDPOPUP )
+ if ( menuprev != menutmp || pmt->trackFlags & TF_SUSPENDPOPUP )
{
/* A sublevel menu was displayed - display the next one
* unless there is another displacement coming up */
if( !MENU_SuspendPopup( pmt, WM_KEYDOWN ) )
- pmt->hCurrentMenu = MENU_ShowSubPopup(pmt->hOwnerWnd,
- pmt->hTopMenu, TRUE, wFlags);
+ pmt->current_menu = MENU_ShowSubPopup(pmt->hOwnerWnd,
+ pmt->top_menu, TRUE, wFlags);
}
}
}
@@ -2936,51 +2902,50 @@ static void MENU_KeyLeft( MTRACKER* pmt, UINT wFlags )
*/
static void MENU_KeyRight( MTRACKER* pmt, UINT wFlags )
{
- HMENU hmenutmp;
- POPUPMENU *menu = MENU_GetMenu( pmt->hTopMenu );
+ POPUPMENU *menutmp;
UINT nextcol;
TRACE("MENU_KeyRight called, cur %p (%s), top %p (%s).\n",
- pmt->hCurrentMenu,
- debugstr_w((MENU_GetMenu(pmt->hCurrentMenu))->items[0].text),
- pmt->hTopMenu, debugstr_w(menu->items[0].text) );
+ pmt->current_menu,
+ debugstr_w(pmt->current_menu->items[0].text),
+ pmt->top_menu, debugstr_w(pmt->top_menu->items[0].text) );
- if ( (menu->wFlags & MF_POPUP) || (pmt->hCurrentMenu != pmt->hTopMenu))
+ if ( (pmt->top_menu->wFlags & MF_POPUP) || (pmt->current_menu != pmt->top_menu))
{
/* If already displaying a popup, try to display sub-popup */
- hmenutmp = pmt->hCurrentMenu;
- pmt->hCurrentMenu = MENU_ShowSubPopup(pmt->hOwnerWnd, hmenutmp, TRUE, wFlags);
+ menutmp = pmt->current_menu;
+ pmt->current_menu = MENU_ShowSubPopup(pmt->hOwnerWnd, menutmp, TRUE, wFlags);
/* if subpopup was displayed then we are done */
- if (hmenutmp != pmt->hCurrentMenu) return;
+ if (menutmp != pmt->current_menu) return;
}
/* Check to see if there's another column */
- if( (nextcol = MENU_GetStartOfNextColumn( pmt->hCurrentMenu )) !=
+ if( (nextcol = MENU_GetStartOfNextColumn( pmt->current_menu )) !=
NO_SELECTED_ITEM ) {
TRACE("Going to %d.\n", nextcol );
- MENU_SelectItem( pmt->hOwnerWnd, pmt->hCurrentMenu,
+ MENU_SelectItem( pmt->hOwnerWnd, pmt->current_menu,
nextcol, TRUE, 0 );
return;
}
- if (!(menu->wFlags & MF_POPUP)) /* menu bar tracking */
+ if (!(pmt->top_menu->wFlags & MF_POPUP)) /* menu bar tracking */
{
- if( pmt->hCurrentMenu != pmt->hTopMenu )
+ if( pmt->current_menu != pmt->top_menu)
{
- MENU_HideSubPopups( pmt->hOwnerWnd, pmt->hTopMenu, FALSE, wFlags );
- hmenutmp = pmt->hCurrentMenu = pmt->hTopMenu;
- } else hmenutmp = 0;
+ MENU_HideSubPopups( pmt->hOwnerWnd, pmt->top_menu, FALSE, wFlags );
+ menutmp = pmt->current_menu = pmt->top_menu;
+ } else menutmp = 0;
/* try to move to the next item */
if( !MENU_DoNextMenu( pmt, VK_RIGHT, wFlags ) )
- MENU_MoveSelection( pmt->hOwnerWnd, pmt->hTopMenu, ITEM_NEXT );
+ MENU_MoveSelection( pmt->hOwnerWnd, pmt->top_menu, ITEM_NEXT );
- if( hmenutmp || pmt->trackFlags & TF_SUSPENDPOPUP )
+ if( menutmp || pmt->trackFlags & TF_SUSPENDPOPUP )
if( !MENU_SuspendPopup(pmt, WM_KEYDOWN) )
- pmt->hCurrentMenu = MENU_ShowSubPopup(pmt->hOwnerWnd,
- pmt->hTopMenu, TRUE, wFlags);
+ pmt->current_menu = MENU_ShowSubPopup(pmt->hOwnerWnd,
+ pmt->top_menu, TRUE, wFlags);
}
}
@@ -2994,11 +2959,10 @@ static void CALLBACK release_capture( BOOL __normal )
*
* Menu tracking code.
*/
-static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
+static BOOL MENU_TrackMenu( POPUPMENU *menu, UINT wFlags, INT x, INT y,
HWND hwnd, const RECT *lprect )
{
MSG msg;
- POPUPMENU *menu;
BOOL fRemove;
INT executedMenuId = -1;
MTRACKER mt;
@@ -3006,18 +2970,17 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
HWND capture_win;
mt.trackFlags = 0;
- mt.hCurrentMenu = hmenu;
- mt.hTopMenu = hmenu;
+ mt.current_menu = mt.top_menu = menu;
mt.hOwnerWnd = WIN_GetFullHandle( hwnd );
mt.pt.x = x;
mt.pt.y = y;
- TRACE("hmenu=%p flags=0x%08x (%d,%d) hwnd=%p %s\n",
- hmenu, wFlags, x, y, hwnd, wine_dbgstr_rect( lprect));
+ TRACE("menu=%p flags=0x%08x (%d,%d) hwnd=%p %s\n",
+ menu, wFlags, x, y, hwnd, wine_dbgstr_rect( lprect));
- if (!(menu = MENU_GetMenu( hmenu )))
+ if (!menu)
{
- WARN("Invalid menu handle %p\n", hmenu);
+ WARN("Invalid menu handle %p\n", menu);
SetLastError(ERROR_INVALID_MENU_HANDLE);
return FALSE;
}
@@ -3025,7 +2988,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
if (wFlags & TPM_BUTTONDOWN)
{
/* Get the result in order to start the tracking or not */
- fRemove = MENU_ButtonDown( &mt, hmenu, wFlags );
+ fRemove = MENU_ButtonDown( &mt, menu, wFlags );
fEndMenu = !fRemove;
}
@@ -3037,7 +3000,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
__TRY while (!fEndMenu)
{
- menu = MENU_GetMenu( mt.hCurrentMenu );
+ menu = mt.current_menu;
if (!menu) /* sometimes happens if I do a window manager close */
break;
@@ -3095,7 +3058,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
mt.pt.y = (short)HIWORD(msg.lParam);
/* Find a menu for this mouse event */
- hmenu = MENU_PtMenu( mt.hTopMenu, mt.pt );
+ menu = MENU_PtMenu( mt.top_menu, mt.pt );
switch(msg.message)
{
@@ -3109,7 +3072,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
case WM_LBUTTONDOWN:
/* If the message belongs to the menu, removes it from the queue */
/* Else, end menu tracking */
- fRemove = MENU_ButtonDown( &mt, hmenu, wFlags );
+ fRemove = MENU_ButtonDown( &mt, menu, wFlags );
fEndMenu = !fRemove;
break;
@@ -3118,9 +3081,9 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
/* fall through */
case WM_LBUTTONUP:
/* Check if a menu was selected by the mouse */
- if (hmenu)
+ if (menu)
{
- executedMenuId = MENU_ButtonUp( &mt, hmenu, wFlags);
+ executedMenuId = MENU_ButtonUp( &mt, menu, wFlags);
TRACE("executedMenuId %d\n", executedMenuId);
/* End the loop if executedMenuId is an item ID */
@@ -3139,8 +3102,8 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
/* the selected menu item must be changed every time */
/* the mouse moves. */
- if (hmenu)
- fEndMenu |= !MENU_MouseMove( &mt, hmenu, wFlags );
+ if (menu)
+ fEndMenu |= !MENU_MouseMove( &mt, menu, wFlags );
} /* switch(msg.message) - mouse */
}
@@ -3160,20 +3123,20 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
case VK_HOME:
case VK_END:
- MENU_SelectItem( mt.hOwnerWnd, mt.hCurrentMenu,
+ MENU_SelectItem( mt.hOwnerWnd, mt.current_menu,
NO_SELECTED_ITEM, FALSE, 0 );
- MENU_MoveSelection( mt.hOwnerWnd, mt.hCurrentMenu,
+ MENU_MoveSelection( mt.hOwnerWnd, mt.current_menu,
(msg.wParam == VK_HOME)? ITEM_NEXT : ITEM_PREV );
break;
case VK_UP:
case VK_DOWN: /* If on menu bar, pull-down the menu */
- menu = MENU_GetMenu( mt.hCurrentMenu );
+ menu = mt.current_menu;
if (!(menu->wFlags & MF_POPUP))
- mt.hCurrentMenu = MENU_ShowSubPopup(mt.hOwnerWnd, mt.hTopMenu, TRUE, wFlags);
+ mt.current_menu = MENU_ShowSubPopup(mt.hOwnerWnd, mt.top_menu, TRUE, wFlags);
else /* otherwise try to move selection */
- MENU_MoveSelection( mt.hOwnerWnd, mt.hCurrentMenu,
+ MENU_MoveSelection( mt.hOwnerWnd, mt.current_menu,
(msg.wParam == VK_UP)? ITEM_PREV : ITEM_NEXT );
break;
@@ -3198,7 +3161,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
hi.iCtrlId = 0;
else
hi.iCtrlId = menu->items[menu->FocusedItem].wID;
- hi.hItemHandle = hmenu;
+ hi.hItemHandle = MENU_GetHandle(menu);
hi.dwContextId = menu->dwContextHelpID;
hi.MousePos = msg.pt;
SendMessageW(hwnd, WM_HELP, 0, (LPARAM)&hi);
@@ -3217,7 +3180,7 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
if (msg.wParam == '\r' || msg.wParam == ' ')
{
- executedMenuId = MENU_ExecFocusedItem(&mt,mt.hCurrentMenu, wFlags);
+ executedMenuId = MENU_ExecFocusedItem(&mt,mt.current_menu, wFlags);
fEndMenu = (executedMenuId != -2);
break;
@@ -3227,15 +3190,15 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
/* We will find a better way real soon... */
if (msg.wParam < 32) break;
- pos = MENU_FindItemByKey( mt.hOwnerWnd, mt.hCurrentMenu,
+ pos = MENU_FindItemByKey( mt.hOwnerWnd, mt.current_menu,
LOWORD(msg.wParam), FALSE );
if (pos == (UINT)-2) fEndMenu = TRUE;
else if (pos == (UINT)-1) MessageBeep(0);
else
{
- MENU_SelectItem( mt.hOwnerWnd, mt.hCurrentMenu, pos,
+ MENU_SelectItem( mt.hOwnerWnd, mt.current_menu, pos,
TRUE, 0 );
- executedMenuId = MENU_ExecFocusedItem(&mt,mt.hCurrentMenu, wFlags);
+ executedMenuId = MENU_ExecFocusedItem(&mt,mt.current_menu, wFlags);
fEndMenu = (executedMenuId != -2);
}
}
@@ -3261,31 +3224,29 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
/* If dropdown is still painted and the close box is clicked on
then the menu will be destroyed as part of the DispatchMessage above.
- This will then invalidate the menu handle in mt.hTopMenu. We should
+ This will then invalidate the menu handle in mt.top_menu. We should
check for this first. */
- if( IsMenu( mt.hTopMenu ) )
+ if( mt.top_menu )
{
- menu = MENU_GetMenu( mt.hTopMenu );
-
if( IsWindow( mt.hOwnerWnd ) )
{
- MENU_HideSubPopups( mt.hOwnerWnd, mt.hTopMenu, FALSE, wFlags );
+ MENU_HideSubPopups( mt.hOwnerWnd, mt.top_menu, FALSE, wFlags );
- if (menu && (menu->wFlags & MF_POPUP))
+ if (mt.top_menu && (mt.top_menu->wFlags & MF_POPUP))
{
- DestroyWindow( menu->hWnd );
- menu->hWnd = 0;
+ DestroyWindow( mt.top_menu->hWnd );
+ mt.top_menu->hWnd = 0;
if (!(wFlags & TPM_NONOTIFY))
- SendMessageW( mt.hOwnerWnd, WM_UNINITMENUPOPUP, (WPARAM)mt.hTopMenu,
- MAKELPARAM(0, IS_SYSTEM_MENU(menu)) );
+ SendMessageW( mt.hOwnerWnd, WM_UNINITMENUPOPUP, (WPARAM)MENU_GetHandle(mt.top_menu),
+ MAKELPARAM(0, IS_SYSTEM_MENU(mt.top_menu)) );
}
- MENU_SelectItem( mt.hOwnerWnd, mt.hTopMenu, NO_SELECTED_ITEM, FALSE, 0 );
+ MENU_SelectItem( mt.hOwnerWnd, mt.top_menu, NO_SELECTED_ITEM, FALSE, 0 );
SendMessageW( mt.hOwnerWnd, WM_MENUSELECT, MAKEWPARAM(0,0xffff), 0 );
}
- /* Reset the variable for hiding menu */
- if( menu ) menu->bTimeToHide = FALSE;
+ /* Reset the variable for hiding mt.top_menu */
+ if( mt.top_menu ) mt.top_menu->bTimeToHide = FALSE;
}
/* The return value is only used by TrackPopupMenu */
@@ -3297,15 +3258,13 @@ static BOOL MENU_TrackMenu( HMENU hmenu, UINT wFlags, INT x, INT y,
/***********************************************************************
* MENU_InitTracking
*/
-static BOOL MENU_InitTracking(HWND hWnd, HMENU hMenu, BOOL bPopup, UINT wFlags)
+static BOOL MENU_InitTracking(HWND hWnd, POPUPMENU *menu, BOOL bPopup, UINT wFlags)
{
- POPUPMENU *menu;
-
- TRACE("hwnd=%p hmenu=%p\n", hWnd, hMenu);
+ TRACE("hwnd=%p menu=%p\n", hWnd, menu);
HideCaret(0);
- if (!(menu = MENU_GetMenu( hMenu ))) return FALSE;
+ if (!menu) return FALSE;
/* This makes the menus of applications built with Delphi work.
* It also enables menus to be displayed in more than one window,
@@ -3315,7 +3274,7 @@ static BOOL MENU_InitTracking(HWND hWnd, HMENU hMenu, BOOL bPopup, UINT wFlags)
if (!top_popup)
{
top_popup = menu->hWnd;
- top_popup_hmenu = hMenu;
+ top_popup_menu = menu;
}
fEndMenu = FALSE;
@@ -3328,7 +3287,7 @@ static BOOL MENU_InitTracking(HWND hWnd, HMENU hMenu, BOOL bPopup, UINT wFlags)
if (!(wFlags & TPM_NONOTIFY))
{
- SendMessageW( hWnd, WM_INITMENU, (WPARAM)hMenu, 0 );
+ SendMessageW( hWnd, WM_INITMENU, (WPARAM)MENU_GetHandle(menu), 0 );
/* If an app changed/recreated menu bar entries in WM_INITMENU
* menu sizes will be recalculated once the menu created/shown.
*/
@@ -3347,7 +3306,7 @@ static BOOL MENU_ExitTracking(HWND hWnd, BOOL bPopup)
SendMessageW( hWnd, WM_EXITMENULOOP, bPopup, 0 );
ShowCaret(0);
top_popup = 0;
- top_popup_hmenu = NULL;
+ top_popup_menu = NULL;
return TRUE;
}
@@ -3366,11 +3325,11 @@ void MENU_TrackMouseMenuBar( HWND hWnd, INT ht, POINT pt )
if (GetWindowLongW( hWnd, GWL_EXSTYLE ) & WS_EX_LAYOUTRTL) wFlags |= TPM_LAYOUTRTL;
if (IsMenu(hMenu))
{
- MENU_InitTracking( hWnd, hMenu, FALSE, wFlags );
+ MENU_InitTracking( hWnd, MENU_GetMenu(hMenu), FALSE, wFlags );
/* fetch the window menu again, it may have changed */
hMenu = (ht == HTSYSMENU) ? get_win_sys_menu( hWnd ) : GetMenu( hWnd );
- MENU_TrackMenu( hMenu, wFlags, pt.x, pt.y, hWnd, NULL );
+ MENU_TrackMenu( MENU_GetMenu(hMenu), wFlags, pt.x, pt.y, hWnd, NULL );
MENU_ExitTracking(hWnd, FALSE);
}
}
@@ -3386,6 +3345,7 @@ void MENU_TrackKbdMenuBar( HWND hwnd, UINT wParam, WCHAR wChar)
UINT uItem = NO_SELECTED_ITEM;
HMENU hTrackMenu;
UINT wFlags = TPM_LEFTALIGN | TPM_LEFTBUTTON;
+ POPUPMENU *trackmenu;
TRACE("hwnd %p wParam 0x%04x wChar 0x%04x\n", hwnd, wParam, wChar);
@@ -3406,16 +3366,18 @@ void MENU_TrackKbdMenuBar( HWND hwnd, UINT wParam, WCHAR wChar)
}
if (GetWindowLongW( hwnd, GWL_EXSTYLE ) & WS_EX_LAYOUTRTL) wFlags |= TPM_LAYOUTRTL;
- if (!IsMenu( hTrackMenu )) return;
+ trackmenu = MENU_GetMenu(hTrackMenu);
+ if (!trackmenu ) return;
- MENU_InitTracking( hwnd, hTrackMenu, FALSE, wFlags );
+ MENU_InitTracking( hwnd, trackmenu, FALSE, wFlags );
/* fetch the window menu again, it may have changed */
hTrackMenu = (wParam & HTSYSMENU) ? get_win_sys_menu( hwnd ) : GetMenu( hwnd );
+ trackmenu = MENU_GetMenu(hTrackMenu);
if( wChar && wChar != ' ' )
{
- uItem = MENU_FindItemByKey( hwnd, hTrackMenu, wChar, (wParam & HTSYSMENU) );
+ uItem = MENU_FindItemByKey( hwnd, trackmenu, wChar, (wParam & HTSYSMENU) );
if ( uItem >= (UINT)(-2) )
{
if( uItem == (UINT)(-1) ) MessageBeep(0);
@@ -3425,18 +3387,18 @@ void MENU_TrackKbdMenuBar( HWND hwnd, UINT wParam, WCHAR wChar)
}
}
- MENU_SelectItem( hwnd, hTrackMenu, uItem, TRUE, 0 );
+ MENU_SelectItem( hwnd, trackmenu, uItem, TRUE, 0 );
if (!(wParam & HTSYSMENU) || wChar == ' ')
{
if( uItem == NO_SELECTED_ITEM )
- MENU_MoveSelection( hwnd, hTrackMenu, ITEM_NEXT );
+ MENU_MoveSelection( hwnd, trackmenu, ITEM_NEXT );
else
PostMessageW( hwnd, WM_KEYDOWN, VK_RETURN, 0 );
}
track_menu:
- MENU_TrackMenu( hTrackMenu, wFlags, 0, 0, hwnd, NULL );
+ MENU_TrackMenu( trackmenu, wFlags, 0, 0, hwnd, NULL );
MENU_ExitTracking( hwnd, FALSE );
}
@@ -3454,8 +3416,6 @@ BOOL WINAPI TrackPopupMenuEx( HMENU hMenu, UINT wFlags, INT x, INT y,
lpTpm ? wine_dbgstr_rect( &lpTpm->rcExclude) : "-" );
/* Parameter check */
- /* FIXME: this check is performed several times, here and in the called
- functions. That could be optimized */
if (!(menu = MENU_GetMenu( hMenu )))
{
SetLastError( ERROR_INVALID_MENU_HANDLE );
@@ -3468,16 +3428,16 @@ BOOL WINAPI TrackPopupMenuEx( HMENU hMenu, UINT wFlags, INT x, INT y,
return FALSE;
}
- if (MENU_InitPopup( hWnd, hMenu, wFlags ))
+ if (MENU_InitPopup( hWnd, menu, wFlags ))
{
- MENU_InitTracking(hWnd, hMenu, TRUE, wFlags);
+ MENU_InitTracking(hWnd, menu, TRUE, wFlags);
/* Send WM_INITMENUPOPUP message only if TPM_NONOTIFY flag is not specified */
if (!(wFlags & TPM_NONOTIFY))
SendMessageW( hWnd, WM_INITMENUPOPUP, (WPARAM)hMenu, 0);
- if (MENU_ShowPopup( hWnd, hMenu, 0, wFlags, x, y, 0, 0 ))
- ret = MENU_TrackMenu( hMenu, wFlags | TPM_POPUPMENU, 0, 0, hWnd,
+ if (MENU_ShowPopup( hWnd, menu, 0, wFlags, x, y, 0, 0 ))
+ ret = MENU_TrackMenu( menu, wFlags | TPM_POPUPMENU, 0, 0, hWnd,
lpTpm ? &lpTpm->rcExclude : NULL );
MENU_ExitTracking(hWnd, TRUE);
@@ -3553,7 +3513,7 @@ LRESULT WINAPI PopupMenuWndProc( HWND hwnd, UINT message, WPARAM wParam, LPARAM
/* zero out global pointer in case resident popup window was destroyed. */
if (hwnd == top_popup) {
top_popup = 0;
- top_popup_hmenu = NULL;
+ top_popup_menu = NULL;
}
break;
@@ -3652,10 +3612,11 @@ BOOL WINAPI ChangeMenuW( HMENU hMenu, UINT pos, LPCWSTR data,
*/
DWORD WINAPI CheckMenuItem( HMENU hMenu, UINT id, UINT flags )
{
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
MENUITEM *item;
DWORD ret;
- if (!(item = MENU_FindItem( &hMenu, &id, flags ))) return -1;
+ if (!(item = MENU_FindItem( &menu, &id, flags ))) return -1;
ret = item->fState & MF_CHECKED;
if (flags & MF_CHECKED) item->fState |= MF_CHECKED;
else item->fState &= ~MF_CHECKED;
@@ -3678,7 +3639,7 @@ BOOL WINAPI EnableMenuItem( HMENU hMenu, UINT wItemID, UINT wFlags )
if (!(menu = MENU_GetMenu(hMenu)))
return (UINT)-1;
- if (!(item = MENU_FindItem( &hMenu, &wItemID, wFlags )))
+ if (!(item = MENU_FindItem( &menu, &wItemID, wFlags )))
return (UINT)-1;
oldflags = item->fState & (MF_GRAYED | MF_DISABLED);
@@ -3718,10 +3679,11 @@ INT WINAPI GetMenuStringA(
UINT wFlags /* [in] MF_ flags */
) {
MENUITEM *item;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
TRACE("menu=%p item=%04x ptr=%p len=%d flags=%04x\n", hMenu, wItemID, str, nMaxSiz, wFlags );
if (str && nMaxSiz) str[0] = '\0';
- if (!(item = MENU_FindItem( &hMenu, &wItemID, wFlags ))) {
+ if (!(item = MENU_FindItem( &menu, &wItemID, wFlags ))) {
SetLastError( ERROR_MENU_ITEM_NOT_FOUND);
return 0;
}
@@ -3741,10 +3703,11 @@ INT WINAPI GetMenuStringW( HMENU hMenu, UINT wItemID,
LPWSTR str, INT nMaxSiz, UINT wFlags )
{
MENUITEM *item;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
TRACE("menu=%p item=%04x ptr=%p len=%d flags=%04x\n", hMenu, wItemID, str, nMaxSiz, wFlags );
if (str && nMaxSiz) str[0] = '\0';
- if (!(item = MENU_FindItem( &hMenu, &wItemID, wFlags ))) {
+ if (!(item = MENU_FindItem( &menu, &wItemID, wFlags ))) {
SetLastError( ERROR_MENU_ITEM_NOT_FOUND);
return 0;
}
@@ -3765,13 +3728,13 @@ INT WINAPI GetMenuStringW( HMENU hMenu, UINT wItemID,
BOOL WINAPI HiliteMenuItem( HWND hWnd, HMENU hMenu, UINT wItemID,
UINT wHilite )
{
- LPPOPUPMENU menu;
+ LPPOPUPMENU menu = MENU_GetMenu(hMenu);
+ MENUITEM *item;
TRACE("(%p, %p, %04x, %04x);\n", hWnd, hMenu, wItemID, wHilite);
- if (!MENU_FindItem( &hMenu, &wItemID, wHilite )) return FALSE;
- if (!(menu = MENU_GetMenu(hMenu))) return FALSE;
+ if (!(item = MENU_FindItem( &menu, &wItemID, wHilite ))) return FALSE;
if (menu->FocusedItem == wItemID) return TRUE;
- MENU_HideSubPopups( hWnd, hMenu, FALSE, 0 );
- MENU_SelectItem( hWnd, hMenu, wItemID, TRUE, 0 );
+ MENU_HideSubPopups( hWnd, menu, FALSE, 0 );
+ MENU_SelectItem( hWnd, menu, wItemID, TRUE, 0 );
return TRUE;
}
@@ -3781,13 +3744,14 @@ BOOL WINAPI HiliteMenuItem( HWND hWnd, HMENU hMenu, UINT wItemID,
*/
UINT WINAPI GetMenuState( HMENU hMenu, UINT wItemID, UINT wFlags )
{
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
MENUITEM *item;
TRACE("(menu=%p, id=%04x, flags=%04x);\n", hMenu, wItemID, wFlags);
- if (!(item = MENU_FindItem( &hMenu, &wItemID, wFlags ))) return -1;
+ if (!(item = MENU_FindItem( &menu, &wItemID, wFlags ))) return -1;
debug_print_menuitem (" item: ", item, "");
if (item->fType & MF_POPUP)
{
- POPUPMENU *menu = MENU_GetMenu( item->hSubMenu );
+ menu = item->submenu;
if (!menu) return -1;
else return (menu->nItems << 8) | ((item->fState|item->fType) & 0xff);
}
@@ -3819,8 +3783,9 @@ INT WINAPI GetMenuItemCount( HMENU hMenu )
UINT WINAPI GetMenuItemID( HMENU hMenu, INT nPos )
{
MENUITEM * lpmi;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
- if (!(lpmi = MENU_FindItem(&hMenu,(UINT*)&nPos,MF_BYPOSITION))) return -1;
+ if (!(lpmi = MENU_FindItem(&menu, (UINT*)&nPos, MF_BYPOSITION))) return -1;
if (lpmi->fType & MF_POPUP) return -1;
return lpmi->wID;
@@ -3947,15 +3912,17 @@ BOOL WINAPI AppendMenuW( HMENU hMenu, UINT flags,
*/
BOOL WINAPI RemoveMenu( HMENU hMenu, UINT nPos, UINT wFlags )
{
- LPPOPUPMENU menu;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
MENUITEM *item;
TRACE("(menu=%p pos=%04x flags=%04x)\n",hMenu, nPos, wFlags);
- if (!(item = MENU_FindItem( &hMenu, &nPos, wFlags ))) return FALSE;
- if (!(menu = MENU_GetMenu(hMenu))) return FALSE;
+ if (!(item = MENU_FindItem( &menu, &nPos, wFlags ))) return FALSE;
/* Remove item */
+ if(item->fType & MF_POPUP)
+ MENU_ReleaseMenu(item->submenu);
+
MENU_FreeItemData( item );
if (--menu->nItems == 0)
@@ -3983,11 +3950,12 @@ BOOL WINAPI RemoveMenu( HMENU hMenu, UINT nPos, UINT wFlags )
*/
BOOL WINAPI DeleteMenu( HMENU hMenu, UINT nPos, UINT wFlags )
{
- MENUITEM *item = MENU_FindItem( &hMenu, &nPos, wFlags );
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
+ MENUITEM *item = MENU_FindItem( &menu, &nPos, wFlags );
if (!item) return FALSE;
- if (item->fType & MF_POPUP) DestroyMenu( item->hSubMenu );
+ if (item->fType & MF_POPUP) DestroyMenu( MENU_GetHandle(item->submenu) );
/* nPos is now the position of the item */
- RemoveMenu( hMenu, nPos, wFlags | MF_BYPOSITION );
+ RemoveMenu( MENU_GetHandle(menu), nPos, wFlags | MF_BYPOSITION );
return TRUE;
}
@@ -3998,6 +3966,7 @@ BOOL WINAPI DeleteMenu( HMENU hMenu, UINT nPos, UINT wFlags )
BOOL WINAPI ModifyMenuW( HMENU hMenu, UINT pos, UINT flags,
UINT_PTR id, LPCWSTR str )
{
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
MENUITEM *item;
MENUITEMINFOW mii;
@@ -4006,8 +3975,8 @@ BOOL WINAPI ModifyMenuW( HMENU hMenu, UINT pos, UINT flags,
else
TRACE("%p %d %04x %04lx %p\n", hMenu, pos, flags, id, str );
- if (!(item = MENU_FindItem( &hMenu, &pos, flags ))) return FALSE;
- MENU_GetMenu(hMenu)->Height = 0; /* force size recalculate */
+ if (!(item = MENU_FindItem( &menu, &pos, flags ))) return FALSE;
+ menu->Height = 0; /* force size recalculate */
MENU_mnu2mnuii( flags, id, str, &mii);
return SetMenuItemInfo_common( item, &mii, TRUE);
}
@@ -4070,8 +4039,9 @@ BOOL WINAPI SetMenuItemBitmaps( HMENU hMenu, UINT nPos, UINT wFlags,
HBITMAP hNewUnCheck, HBITMAP hNewCheck)
{
MENUITEM *item;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
- if (!(item = MENU_FindItem( &hMenu, &nPos, wFlags ))) return FALSE;
+ if (!(item = MENU_FindItem( &menu, &nPos, wFlags ))) return FALSE;
if (!hNewCheck && !hNewUnCheck)
{
@@ -4098,6 +4068,7 @@ HMENU WINAPI CreateMenu(void)
if (!(menu = HeapAlloc( GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(*menu) ))) return 0;
menu->FocusedItem = NO_SELECTED_ITEM;
menu->bTimeToHide = FALSE;
+ menu->refcount = 1;
if (!(hMenu = alloc_user_handle( &menu->obj, USER_MENU ))) HeapFree( GetProcessHeap(), 0, menu );
@@ -4106,18 +4077,13 @@ HMENU WINAPI CreateMenu(void)
return hMenu;
}
-
-/**********************************************************************
- * DestroyMenu (USER32.@)
- */
-BOOL WINAPI DestroyMenu( HMENU hMenu )
+static BOOL MENU_ReleaseMenu( POPUPMENU *lppop )
{
- LPPOPUPMENU lppop;
+ LONG ref;
- TRACE("(%p)\n", hMenu);
-
- if (!(lppop = free_user_handle( hMenu, USER_MENU ))) return FALSE;
- if (lppop == OBJ_OTHER_PROCESS) return FALSE;
+ ref = InterlockedDecrement(&lppop->refcount);
+ if(ref)
+ return TRUE;
/* DestroyMenu should not destroy system menu popup owner */
if ((lppop->wFlags & (MF_POPUP | MF_SYSMENU)) == MF_POPUP && lppop->hWnd)
@@ -4132,15 +4098,31 @@ BOOL WINAPI DestroyMenu( HMENU hMenu )
MENUITEM *item = lppop->items;
for (i = lppop->nItems; i > 0; i--, item++)
{
- if (item->fType & MF_POPUP) DestroyMenu(item->hSubMenu);
+ if (item->fType & MF_POPUP) MENU_ReleaseMenu(item->submenu);
MENU_FreeItemData( item );
}
HeapFree( GetProcessHeap(), 0, lppop->items );
}
HeapFree( GetProcessHeap(), 0, lppop );
+
return TRUE;
}
+/**********************************************************************
+ * DestroyMenu (USER32.@)
+ */
+BOOL WINAPI DestroyMenu( HMENU hMenu )
+{
+ POPUPMENU *lppop;
+
+ TRACE("(%p)\n", hMenu);
+
+ if (!(lppop = free_user_handle( hMenu, USER_MENU ))) return FALSE;
+ if (lppop == OBJ_OTHER_PROCESS) return FALSE;
+
+ return MENU_ReleaseMenu(lppop);
+}
+
/**********************************************************************
* GetSystemMenu (USER32.@)
@@ -4279,13 +4261,13 @@ BOOL WINAPI GetMenuBarInfo( HWND hwnd, LONG idObject, LONG idItem, PMENUBARINFO
pmbi->hMenu = hmenu;
pmbi->hwndMenu = NULL;
- pmbi->fBarFocused = top_popup_hmenu == hmenu;
+ pmbi->fBarFocused = (top_popup_menu == menu);
if (idItem)
{
pmbi->fFocused = menu->FocusedItem == idItem - 1;
if (pmbi->fFocused && (menu->items[idItem - 1].fType & MF_POPUP))
{
- menu = MENU_GetMenu(menu->items[idItem - 1].hSubMenu);
+ menu = menu->items[idItem - 1].submenu;
if (menu)
pmbi->hwndMenu = menu->hWnd;
}
@@ -4354,10 +4336,11 @@ BOOL WINAPI SetMenu( HWND hWnd, HMENU hMenu )
HMENU WINAPI GetSubMenu( HMENU hMenu, INT nPos )
{
MENUITEM * lpmi;
+ POPUPMENU *menu = MENU_GetMenu(hMenu);
- if (!(lpmi = MENU_FindItem(&hMenu,(UINT*)&nPos,MF_BYPOSITION))) return 0;
+ if (!(lpmi = MENU_FindItem(&menu, (UINT*)&nPos, MF_BYPOSITION))) return 0;
if (!(lpmi->fType & MF_POPUP)) return 0;
- return lpmi->hSubMenu;
+ return MENU_GetHandle(lpmi->submenu);
}
@@ -4435,7 +4418,7 @@ DWORD WINAPI DrawMenuBarTemp(HWND hwnd, HDC hDC, LPRECT lprect, HMENU hMenu, HFO
for (i = 0; i < lppop->nItems; i++)
{
- MENU_DrawMenuItem( hwnd, hMenu, hwnd,
+ MENU_DrawMenuItem( hwnd, lppop, hwnd,
hDC, &lppop->items[i], lppop->Height, TRUE, ODA_DRAWENTIRE );
}
retvalue = lppop->Height;
@@ -4561,7 +4544,8 @@ BOOL WINAPI IsMenu(HMENU hmenu)
static BOOL GetMenuItemInfo_common ( HMENU hmenu, UINT item, BOOL bypos,
LPMENUITEMINFOW lpmii, BOOL unicode)
{
- MENUITEM *menu = MENU_FindItem (&hmenu, &item, bypos ? MF_BYPOSITION : 0);
+ POPUPMENU *popup = MENU_GetMenu(hmenu);
+ MENUITEM *menu = MENU_FindItem (&popup, &item, bypos ? MF_BYPOSITION : 0);
debug_print_menuitem("GetMenuItemInfo_common: ", menu, "");
@@ -4644,7 +4628,7 @@ static BOOL GetMenuItemInfo_common ( HMENU hmenu, UINT item, BOOL bypos,
lpmii->wID = menu->wID;
if (lpmii->fMask & MIIM_SUBMENU)
- lpmii->hSubMenu = menu->hSubMenu;
+ lpmii->hSubMenu = MENU_GetHandle(menu->submenu);
else {
/* hSubMenu is always cleared
* (not on Win9x/ME ) */
@@ -4741,13 +4725,12 @@ static int MENU_depth( POPUPMENU *pmenu, int depth)
item = pmenu->items;
subdepth = depth;
for( i = 0; i < pmenu->nItems && subdepth <= MAXMENUDEPTH; i++, item++){
- POPUPMENU *psubmenu = item->hSubMenu ? MENU_GetMenu( item->hSubMenu) : NULL;
- if( psubmenu){
- int bdepth = MENU_depth( psubmenu, depth);
+ if( item->submenu){
+ int bdepth = MENU_depth( item->submenu, depth);
if( bdepth > subdepth) subdepth = bdepth;
}
if( subdepth > MAXMENUDEPTH)
- TRACE("<- hmenu %p\n", item->hSubMenu);
+ TRACE("<- menu %p\n", item->submenu);
}
return subdepth;
}
@@ -4787,24 +4770,29 @@ static BOOL SetMenuItemInfo_common(MENUITEM * menu,
menu->wID = lpmii->wID;
if (lpmii->fMask & MIIM_SUBMENU) {
- menu->hSubMenu = lpmii->hSubMenu;
- if (menu->hSubMenu) {
- POPUPMENU *subMenu = MENU_GetMenu(menu->hSubMenu);
- if (subMenu) {
- if( MENU_depth( subMenu, 0) > MAXMENUDEPTH) {
+ if(menu->fType & MF_POPUP){
+ if(menu->submenu)
+ InterlockedDecrement(&menu->submenu->refcount);
+ }
+
+ if (lpmii->hSubMenu) {
+ menu->submenu = MENU_GetMenu(lpmii->hSubMenu);
+ if (menu->submenu) {
+ if( MENU_depth( menu->submenu, 0) > MAXMENUDEPTH) {
ERR( "Loop detected in menu hierarchy or maximum menu depth exceeded!\n");
- menu->hSubMenu = 0;
+ menu->submenu = NULL;
return FALSE;
}
- subMenu->wFlags |= MF_POPUP;
- menu->fType |= MF_POPUP;
- } else {
+ menu->submenu->wFlags |= MF_POPUP;
+ menu->fType |= MF_POPUP;
+ InterlockedIncrement(&menu->submenu->refcount);
+ } else {
SetLastError( ERROR_INVALID_PARAMETER);
return FALSE;
}
- }
- else
- menu->fType &= ~MF_POPUP;
+ }
+ else
+ menu->fType &= ~MF_POPUP;
}
if (lpmii->fMask & MIIM_CHECKMARKS)
@@ -4876,12 +4864,13 @@ BOOL WINAPI SetMenuItemInfoA(HMENU hmenu, UINT item, BOOL bypos,
const MENUITEMINFOA *lpmii)
{
MENUITEMINFOW mii;
+ POPUPMENU *menu = MENU_GetMenu(hmenu);
TRACE("hmenu %p, item %u, by pos %d, info %p\n", hmenu, item, bypos, lpmii);
if (!MENU_NormalizeMenuItemInfoStruct( (const MENUITEMINFOW *)lpmii, &mii )) return FALSE;
- return SetMenuItemInfo_common(MENU_FindItem(&hmenu, &item, bypos? MF_BYPOSITION : 0),
+ return SetMenuItemInfo_common(MENU_FindItem(&menu, &item, bypos? MF_BYPOSITION : 0),
&mii, FALSE);
}
@@ -4892,11 +4881,12 @@ BOOL WINAPI SetMenuItemInfoW(HMENU hmenu, UINT item, BOOL bypos,
const MENUITEMINFOW *lpmii)
{
MENUITEMINFOW mii;
+ POPUPMENU *menu = MENU_GetMenu(hmenu);
TRACE("hmenu %p, item %u, by pos %d, info %p\n", hmenu, item, bypos, lpmii);
if (!MENU_NormalizeMenuItemInfoStruct( lpmii, &mii )) return FALSE;
- return SetMenuItemInfo_common(MENU_FindItem(&hmenu,
+ return SetMenuItemInfo_common(MENU_FindItem(&menu,
&item, bypos? MF_BYPOSITION : 0), &mii, TRUE);
}
@@ -4977,11 +4967,11 @@ UINT WINAPI GetMenuDefaultItem(HMENU hmenu, UINT bypos, UINT flags)
/* default: don't return disabled items */
if ( (!(GMDI_USEDISABLED & flags)) && (item->fState & MFS_DISABLED )) return -1;
- /* search rekursiv when needed */
+ /* search recursively when needed */
if ( (item->fType & MF_POPUP) && (flags & GMDI_GOINTOPOPUPS) )
{
UINT ret;
- ret = GetMenuDefaultItem( item->hSubMenu, bypos, flags );
+ ret = GetMenuDefaultItem( MENU_GetHandle(item->submenu), bypos, flags );
if ( -1 != ret ) return ret;
/* when item not found in submenu, return the popup item */
@@ -5037,7 +5027,7 @@ BOOL WINAPI CheckMenuRadioItem(HMENU hMenu,
BOOL done = FALSE;
UINT i;
MENUITEM *mi_first = NULL, *mi_check;
- HMENU m_first, m_check;
+ POPUPMENU *m_first, *m_check;
for (i = first; i <= last; i++)
{
@@ -5045,7 +5035,7 @@ BOOL WINAPI CheckMenuRadioItem(HMENU hMenu,
if (!mi_first)
{
- m_first = hMenu;
+ m_first = MENU_GetMenu(hMenu);
mi_first = MENU_FindItem(&m_first, &pos, bypos);
if (!mi_first) continue;
mi_check = mi_first;
@@ -5053,7 +5043,7 @@ BOOL WINAPI CheckMenuRadioItem(HMENU hMenu,
}
else
{
- m_check = hMenu;
+ m_check = MENU_GetMenu(hMenu);
mi_check = MENU_FindItem(&m_check, &pos, bypos);
if (!mi_check) continue;
}
@@ -5089,18 +5079,17 @@ BOOL WINAPI CheckMenuRadioItem(HMENU hMenu,
BOOL WINAPI GetMenuItemRect (HWND hwnd, HMENU hMenu, UINT uItem,
LPRECT rect)
{
- POPUPMENU *itemMenu;
+ POPUPMENU *itemMenu = MENU_GetMenu(hMenu);
MENUITEM *item;
HWND referenceHwnd;
TRACE("(%p,%p,%d,%p)\n", hwnd, hMenu, uItem, rect);
- item = MENU_FindItem (&hMenu, &uItem, MF_BYPOSITION);
+ item = MENU_FindItem (&itemMenu, &uItem, MF_BYPOSITION);
referenceHwnd = hwnd;
if(!hwnd)
{
- itemMenu = MENU_GetMenu(hMenu);
if (itemMenu == NULL)
return FALSE;
@@ -5126,10 +5115,9 @@ BOOL WINAPI GetMenuItemRect (HWND hwnd, HMENU hMenu, UINT uItem,
* actually use the items to draw the menu
* (recalculate and/or redraw)
*/
-static BOOL menu_SetMenuInfo( HMENU hMenu, LPCMENUINFO lpmi)
+static BOOL menu_SetMenuInfo( POPUPMENU *menu, LPCMENUINFO lpmi)
{
- POPUPMENU *menu;
- if( !(menu = MENU_GetMenu(hMenu))) return FALSE;
+ if( !menu ) return FALSE;
if (lpmi->fMask & MIM_BACKGROUND)
menu->hbrBack = lpmi->hbrBack;
@@ -5151,7 +5139,7 @@ static BOOL menu_SetMenuInfo( HMENU hMenu, LPCMENUINFO lpmi)
MENUITEM *item = menu->items;
for( i = menu->nItems; i; i--, item++)
if( item->fType & MF_POPUP)
- menu_SetMenuInfo( item->hSubMenu, lpmi);
+ menu_SetMenuInfo( item->submenu, lpmi);
}
return TRUE;
}
@@ -5159,7 +5147,7 @@ static BOOL menu_SetMenuInfo( HMENU hMenu, LPCMENUINFO lpmi)
BOOL WINAPI SetMenuInfo (HMENU hMenu, LPCMENUINFO lpmi)
{
TRACE("(%p %p)\n", hMenu, lpmi);
- if( lpmi && (lpmi->cbSize == sizeof( MENUINFO)) && (menu_SetMenuInfo( hMenu, lpmi))) {
+ if( lpmi && (lpmi->cbSize == sizeof( MENUINFO)) && (menu_SetMenuInfo( MENU_GetMenu(hMenu), lpmi))) {
if( lpmi->fMask & MIM_STYLE) {
if (lpmi->dwStyle & MNS_AUTODISMISS) FIXME("MNS_AUTODISMISS unimplemented\n");
if (lpmi->dwStyle & MNS_DRAGDROP) FIXME("MNS_DRAGDROP unimplemented\n");
@@ -5309,17 +5297,20 @@ static BOOL translate_accelerator( HWND hWnd, UINT message, WPARAM wParam, LPARA
mesg = 1;
else
{
- HMENU hMenu, hSubMenu, hSysMenu;
+ HMENU hMenu, hSysMenu;
+ POPUPMENU *menu, *subMenu, *sysMenu;
UINT uSysStat = (UINT)-1, uStat = (UINT)-1, nPos;
hMenu = (GetWindowLongW( hWnd, GWL_STYLE ) & WS_CHILD) ? 0 : GetMenu(hWnd);
+ menu = MENU_GetMenu(hMenu);
hSysMenu = get_win_sys_menu( hWnd );
+ sysMenu = MENU_GetMenu(hSysMenu);
/* find menu item and ask application to initialize it */
/* 1. in the system menu */
- hSubMenu = hSysMenu;
+ subMenu = sysMenu;
nPos = cmd;
- if(MENU_FindItem(&hSubMenu, &nPos, MF_BYCOMMAND))
+ if(MENU_FindItem(&subMenu, &nPos, MF_BYCOMMAND))
{
if (GetCapture())
mesg = 2;
@@ -5328,20 +5319,20 @@ static BOOL translate_accelerator( HWND hWnd, UINT message, WPARAM wParam, LPARA
else
{
SendMessageW(hWnd, WM_INITMENU, (WPARAM)hSysMenu, 0L);
- if(hSubMenu != hSysMenu)
+ if(subMenu != sysMenu)
{
- nPos = MENU_FindSubMenu(&hSysMenu, hSubMenu);
- TRACE_(accel)("hSysMenu = %p, hSubMenu = %p, nPos = %d\n", hSysMenu, hSubMenu, nPos);
- SendMessageW(hWnd, WM_INITMENUPOPUP, (WPARAM)hSubMenu, MAKELPARAM(nPos, TRUE));
+ nPos = MENU_FindSubMenu(&sysMenu, subMenu);
+ TRACE_(accel)("sysMenu = %p, subMenu = %p, nPos = %d\n", sysMenu, subMenu, nPos);
+ SendMessageW(hWnd, WM_INITMENUPOPUP, (WPARAM)MENU_GetHandle(subMenu), MAKELPARAM(nPos, TRUE));
}
uSysStat = GetMenuState(GetSubMenu(hSysMenu, 0), cmd, MF_BYCOMMAND);
}
}
else /* 2. in the window's menu */
{
- hSubMenu = hMenu;
+ subMenu = menu;
nPos = cmd;
- if(MENU_FindItem(&hSubMenu, &nPos, MF_BYCOMMAND))
+ if(MENU_FindItem(&subMenu, &nPos, MF_BYCOMMAND))
{
if (GetCapture())
mesg = 2;
@@ -5350,11 +5341,12 @@ static BOOL translate_accelerator( HWND hWnd, UINT message, WPARAM wParam, LPARA
else
{
SendMessageW(hWnd, WM_INITMENU, (WPARAM)hMenu, 0L);
- if(hSubMenu != hMenu)
+ if(subMenu != menu)
{
- nPos = MENU_FindSubMenu(&hMenu, hSubMenu);
- TRACE_(accel)("hMenu = %p, hSubMenu = %p, nPos = %d\n", hMenu, hSubMenu, nPos);
- SendMessageW(hWnd, WM_INITMENUPOPUP, (WPARAM)hSubMenu, MAKELPARAM(nPos, FALSE));
+ nPos = MENU_FindSubMenu(&menu, subMenu);
+ hMenu = MENU_GetHandle(menu);
+ TRACE_(accel)("hMenu = %p, subMenu = %p, nPos = %d\n", hMenu, subMenu, nPos);
+ SendMessageW(hWnd, WM_INITMENUPOPUP, (WPARAM)MENU_GetHandle(subMenu), MAKELPARAM(nPos, FALSE));
}
uStat = GetMenuState(hMenu, cmd, MF_BYCOMMAND);
}
diff --git a/dlls/user32/tests/menu.c b/dlls/user32/tests/menu.c
index 593292d..9cf8af6 100644
--- a/dlls/user32/tests/menu.c
+++ b/dlls/user32/tests/menu.c
@@ -526,9 +526,7 @@ static void test_subpopup_locked_by_menu(void)
SetLastError( 0xdeadbeef);
ret = TrackPopupMenu( hmenu, TPM_RETURNCMD, 100,100, 0, hwnd, NULL);
gle = GetLastError();
- todo_wine {
- ok( ret == itemid , "TrackPopupMenu returned %d error is %d\n", ret, gle);
- }
+ ok( ret == itemid , "TrackPopupMenu returned %d error is %d\n", ret, gle);
ok( gle == 0 ||
broken(gle == 0xdeadbeef) || /* wow64 */
broken(gle == ERROR_INVALID_PARAMETER), /* win2k0 */
--
1.9.2
More information about the wine-patches
mailing list