mirror of
git://source.winehq.org/git/wine.git
synced 2024-09-01 00:13:37 +00:00
win32u: Move get_menu_item_info implementation from user32.
Signed-off-by: Jacek Caban <jacek@codeweavers.com>
This commit is contained in:
parent
4a53c479e8
commit
7099c8d7e8
|
@ -96,91 +96,6 @@ const struct builtin_class_descr MENU_builtin_class =
|
|||
};
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* debug_print_menuitem
|
||||
*
|
||||
* Print a menuitem in readable form.
|
||||
*/
|
||||
|
||||
#define debug_print_menuitem(pre, mp, post) \
|
||||
do { if (TRACE_ON(menu)) do_debug_print_menuitem(pre, mp, post); } while (0)
|
||||
|
||||
#define MENUOUT(text) \
|
||||
TRACE("%s%s", (count++ ? "," : ""), (text))
|
||||
|
||||
#define MENUFLAG(bit,text) \
|
||||
do { \
|
||||
if (flags & (bit)) { flags &= ~(bit); MENUOUT ((text)); } \
|
||||
} while (0)
|
||||
|
||||
static void do_debug_print_menuitem(const char *prefix, const MENUITEM *mp,
|
||||
const char *postfix)
|
||||
{
|
||||
static const char * const hbmmenus[] = { "HBMMENU_CALLBACK", "", "HBMMENU_SYSTEM",
|
||||
"HBMMENU_MBAR_RESTORE", "HBMMENU_MBAR_MINIMIZE", "UNKNOWN BITMAP", "HBMMENU_MBAR_CLOSE",
|
||||
"HBMMENU_MBAR_CLOSE_D", "HBMMENU_MBAR_MINIMIZE_D", "HBMMENU_POPUP_CLOSE",
|
||||
"HBMMENU_POPUP_RESTORE", "HBMMENU_POPUP_MAXIMIZE", "HBMMENU_POPUP_MINIMIZE"};
|
||||
TRACE("%s ", prefix);
|
||||
if (mp) {
|
||||
UINT flags = mp->fType;
|
||||
TRACE( "{ ID=0x%Ix", mp->wID);
|
||||
if ( mp->hSubMenu)
|
||||
TRACE( ", Sub=%p", mp->hSubMenu);
|
||||
if (flags) {
|
||||
int count = 0;
|
||||
TRACE( ", fType=");
|
||||
MENUFLAG( MFT_SEPARATOR, "sep");
|
||||
MENUFLAG( MFT_OWNERDRAW, "own");
|
||||
MENUFLAG( MFT_BITMAP, "bit");
|
||||
MENUFLAG(MF_POPUP, "pop");
|
||||
MENUFLAG(MFT_MENUBARBREAK, "barbrk");
|
||||
MENUFLAG(MFT_MENUBREAK, "brk");
|
||||
MENUFLAG(MFT_RADIOCHECK, "radio");
|
||||
MENUFLAG(MFT_RIGHTORDER, "rorder");
|
||||
MENUFLAG(MF_SYSMENU, "sys");
|
||||
MENUFLAG(MFT_RIGHTJUSTIFY, "right"); /* same as MF_HELP */
|
||||
if (flags)
|
||||
TRACE( "+0x%x", flags);
|
||||
}
|
||||
flags = mp->fState;
|
||||
if (flags) {
|
||||
int count = 0;
|
||||
TRACE( ", State=");
|
||||
MENUFLAG(MFS_GRAYED, "grey");
|
||||
MENUFLAG(MFS_DEFAULT, "default");
|
||||
MENUFLAG(MFS_DISABLED, "dis");
|
||||
MENUFLAG(MFS_CHECKED, "check");
|
||||
MENUFLAG(MFS_HILITE, "hi");
|
||||
MENUFLAG(MF_USECHECKBITMAPS, "usebit");
|
||||
MENUFLAG(MF_MOUSESELECT, "mouse");
|
||||
if (flags)
|
||||
TRACE( "+0x%x", flags);
|
||||
}
|
||||
if (mp->hCheckBit)
|
||||
TRACE( ", Chk=%p", mp->hCheckBit);
|
||||
if (mp->hUnCheckBit)
|
||||
TRACE( ", Unc=%p", mp->hUnCheckBit);
|
||||
if (mp->text)
|
||||
TRACE( ", Text=%s", debugstr_w(mp->text));
|
||||
if (mp->dwItemData)
|
||||
TRACE( ", ItemData=0x%08Ix", mp->dwItemData);
|
||||
if (mp->hbmpItem)
|
||||
{
|
||||
if( IS_MAGIC_BITMAP(mp->hbmpItem))
|
||||
TRACE( ", hbitmap=%s", hbmmenus[ (INT_PTR)mp->hbmpItem + 1]);
|
||||
else
|
||||
TRACE( ", hbitmap=%p", mp->hbmpItem);
|
||||
}
|
||||
TRACE( " }");
|
||||
} else
|
||||
TRACE( "NULL");
|
||||
TRACE(" %s\n", postfix);
|
||||
}
|
||||
|
||||
#undef MENUOUT
|
||||
#undef MENUFLAG
|
||||
|
||||
|
||||
/***********************************************************************
|
||||
* MENU_GetMenu
|
||||
*
|
||||
|
@ -1012,122 +927,6 @@ BOOL WINAPI IsMenu( HMENU menu )
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
/**********************************************************************
|
||||
* GetMenuItemInfo_common
|
||||
*/
|
||||
|
||||
static BOOL GetMenuItemInfo_common ( HMENU hmenu, UINT id, BOOL bypos,
|
||||
LPMENUITEMINFOW lpmii, BOOL unicode)
|
||||
{
|
||||
POPUPMENU *menu;
|
||||
MENUITEM *item;
|
||||
UINT pos;
|
||||
|
||||
menu = find_menu_item(hmenu, id, bypos ? MF_BYPOSITION : 0, &pos);
|
||||
|
||||
item = menu ? &menu->items[pos] : NULL;
|
||||
|
||||
debug_print_menuitem("GetMenuItemInfo_common: ", item, "");
|
||||
|
||||
if (!menu)
|
||||
{
|
||||
SetLastError( ERROR_MENU_ITEM_NOT_FOUND);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if( lpmii->fMask & MIIM_TYPE) {
|
||||
if( lpmii->fMask & ( MIIM_STRING | MIIM_FTYPE | MIIM_BITMAP)) {
|
||||
release_menu_ptr(menu);
|
||||
WARN("invalid combination of fMask bits used\n");
|
||||
/* this does not happen on Win9x/ME */
|
||||
SetLastError( ERROR_INVALID_PARAMETER);
|
||||
return FALSE;
|
||||
}
|
||||
lpmii->fType = item->fType & MENUITEMINFO_TYPE_MASK;
|
||||
if (item->hbmpItem && !IS_MAGIC_BITMAP(item->hbmpItem))
|
||||
lpmii->fType |= MFT_BITMAP;
|
||||
lpmii->hbmpItem = item->hbmpItem; /* not on Win9x/ME */
|
||||
if( lpmii->fType & MFT_BITMAP) {
|
||||
lpmii->dwTypeData = (LPWSTR) item->hbmpItem;
|
||||
lpmii->cch = 0;
|
||||
} else if( lpmii->fType & (MFT_OWNERDRAW | MFT_SEPARATOR)) {
|
||||
/* this does not happen on Win9x/ME */
|
||||
lpmii->dwTypeData = 0;
|
||||
lpmii->cch = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* copy the text string */
|
||||
if ((lpmii->fMask & (MIIM_TYPE|MIIM_STRING))) {
|
||||
if (!item->text) {
|
||||
if(lpmii->dwTypeData && lpmii->cch) {
|
||||
if( unicode)
|
||||
*((WCHAR *)lpmii->dwTypeData) = 0;
|
||||
else
|
||||
*((CHAR *)lpmii->dwTypeData) = 0;
|
||||
}
|
||||
lpmii->cch = 0;
|
||||
} else {
|
||||
int len;
|
||||
if (unicode)
|
||||
{
|
||||
len = lstrlenW(item->text);
|
||||
if(lpmii->dwTypeData && lpmii->cch)
|
||||
lstrcpynW(lpmii->dwTypeData, item->text, lpmii->cch);
|
||||
}
|
||||
else
|
||||
{
|
||||
len = WideCharToMultiByte( CP_ACP, 0, item->text, -1, NULL,
|
||||
0, NULL, NULL ) - 1;
|
||||
if(lpmii->dwTypeData && lpmii->cch)
|
||||
if (!WideCharToMultiByte( CP_ACP, 0, item->text, -1,
|
||||
(LPSTR)lpmii->dwTypeData, lpmii->cch, NULL, NULL ))
|
||||
((LPSTR)lpmii->dwTypeData)[lpmii->cch - 1] = 0;
|
||||
}
|
||||
/* if we've copied a substring we return its length */
|
||||
if(lpmii->dwTypeData && lpmii->cch)
|
||||
if (lpmii->cch <= len + 1)
|
||||
lpmii->cch--;
|
||||
else
|
||||
lpmii->cch = len;
|
||||
else {
|
||||
/* return length of string */
|
||||
/* not on Win9x/ME if fType & MFT_BITMAP */
|
||||
lpmii->cch = len;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (lpmii->fMask & MIIM_FTYPE)
|
||||
lpmii->fType = item->fType & MENUITEMINFO_TYPE_MASK;
|
||||
|
||||
if (lpmii->fMask & MIIM_BITMAP)
|
||||
lpmii->hbmpItem = item->hbmpItem;
|
||||
|
||||
if (lpmii->fMask & MIIM_STATE)
|
||||
lpmii->fState = item->fState & MENUITEMINFO_STATE_MASK;
|
||||
|
||||
if (lpmii->fMask & MIIM_ID)
|
||||
lpmii->wID = item->wID;
|
||||
|
||||
if (lpmii->fMask & MIIM_SUBMENU)
|
||||
lpmii->hSubMenu = item->hSubMenu;
|
||||
else {
|
||||
/* hSubMenu is always cleared
|
||||
* (not on Win9x/ME ) */
|
||||
lpmii->hSubMenu = 0;
|
||||
}
|
||||
|
||||
if (lpmii->fMask & MIIM_CHECKMARKS) {
|
||||
lpmii->hbmpChecked = item->hCheckBit;
|
||||
lpmii->hbmpUnchecked = item->hUnCheckBit;
|
||||
}
|
||||
if (lpmii->fMask & MIIM_DATA)
|
||||
lpmii->dwItemData = item->dwItemData;
|
||||
|
||||
release_menu_ptr(menu);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/**********************************************************************
|
||||
* GetMenuItemInfoA (USER32.@)
|
||||
|
@ -1144,10 +943,10 @@ BOOL WINAPI GetMenuItemInfoA( HMENU hmenu, UINT item, BOOL bypos,
|
|||
}
|
||||
memcpy( &mii, lpmii, lpmii->cbSize);
|
||||
mii.cbSize = sizeof( mii);
|
||||
ret = GetMenuItemInfo_common (hmenu, item, bypos,
|
||||
(LPMENUITEMINFOW)&mii, FALSE);
|
||||
ret = NtUserThunkedMenuItemInfo( hmenu, item, bypos ? MF_BYPOSITION : 0,
|
||||
NtUserGetMenuItemInfoA, (MENUITEMINFOW *)&mii, NULL );
|
||||
mii.cbSize = lpmii->cbSize;
|
||||
memcpy( lpmii, &mii, mii.cbSize);
|
||||
memcpy( lpmii, &mii, mii.cbSize );
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -1166,9 +965,10 @@ BOOL WINAPI GetMenuItemInfoW( HMENU hmenu, UINT item, BOOL bypos,
|
|||
}
|
||||
memcpy( &mii, lpmii, lpmii->cbSize);
|
||||
mii.cbSize = sizeof( mii);
|
||||
ret = GetMenuItemInfo_common (hmenu, item, bypos, &mii, TRUE);
|
||||
ret = NtUserThunkedMenuItemInfo( hmenu, item, bypos ? MF_BYPOSITION : 0,
|
||||
NtUserGetMenuItemInfoW, &mii, NULL );
|
||||
mii.cbSize = lpmii->cbSize;
|
||||
memcpy( lpmii, &mii, mii.cbSize);
|
||||
memcpy( lpmii, &mii, mii.cbSize );
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
|
|
@ -992,6 +992,123 @@ UINT get_menu_state( HMENU handle, UINT item_id, UINT flags )
|
|||
return state;
|
||||
}
|
||||
|
||||
static BOOL get_menu_item_info( HMENU handle, UINT id, UINT flags, MENUITEMINFOW *info, BOOL ansi )
|
||||
{
|
||||
POPUPMENU *menu;
|
||||
MENUITEM *item;
|
||||
UINT pos;
|
||||
|
||||
if (!info || info->cbSize != sizeof(*info))
|
||||
{
|
||||
SetLastError( ERROR_INVALID_PARAMETER );
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
menu = find_menu_item( handle, id, flags, &pos );
|
||||
item = menu ? &menu->items[pos] : NULL;
|
||||
TRACE( "%s\n", debugstr_menuitem( item ));
|
||||
if (!menu)
|
||||
{
|
||||
SetLastError( ERROR_MENU_ITEM_NOT_FOUND);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if (info->fMask & MIIM_TYPE)
|
||||
{
|
||||
if (info->fMask & ( MIIM_STRING | MIIM_FTYPE | MIIM_BITMAP))
|
||||
{
|
||||
release_menu_ptr( menu );
|
||||
WARN( "invalid combination of fMask bits used\n" );
|
||||
/* this does not happen on Win9x/ME */
|
||||
SetLastError( ERROR_INVALID_PARAMETER );
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
info->fType = item->fType & MENUITEMINFO_TYPE_MASK;
|
||||
if (item->hbmpItem && !IS_MAGIC_BITMAP(item->hbmpItem))
|
||||
info->fType |= MFT_BITMAP;
|
||||
info->hbmpItem = item->hbmpItem; /* not on Win9x/ME */
|
||||
if (info->fType & MFT_BITMAP)
|
||||
{
|
||||
info->dwTypeData = (WCHAR *)item->hbmpItem;
|
||||
info->cch = 0;
|
||||
}
|
||||
else if (info->fType & (MFT_OWNERDRAW | MFT_SEPARATOR))
|
||||
{
|
||||
/* this does not happen on Win9x/ME */
|
||||
info->dwTypeData = 0;
|
||||
info->cch = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* copy the text string */
|
||||
if ((info->fMask & (MIIM_TYPE|MIIM_STRING)))
|
||||
{
|
||||
if (!item->text)
|
||||
{
|
||||
if (info->dwTypeData && info->cch)
|
||||
{
|
||||
if (ansi)
|
||||
*((char *)info->dwTypeData) = 0;
|
||||
else
|
||||
*((WCHAR *)info->dwTypeData) = 0;
|
||||
}
|
||||
info->cch = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
DWORD len, text_len;
|
||||
if (ansi)
|
||||
{
|
||||
text_len = wcslen( item->text );
|
||||
len = win32u_wctomb_size( &ansi_cp, item->text, text_len );
|
||||
if (info->dwTypeData && info->cch)
|
||||
if (!win32u_wctomb( &ansi_cp, (char *)info->dwTypeData, info->cch,
|
||||
item->text, text_len + 1 ))
|
||||
((char *)info->dwTypeData)[info->cch - 1] = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
len = lstrlenW( item->text );
|
||||
if (info->dwTypeData && info->cch)
|
||||
lstrcpynW( info->dwTypeData, item->text, info->cch );
|
||||
}
|
||||
|
||||
if (info->dwTypeData && info->cch)
|
||||
{
|
||||
/* if we've copied a substring we return its length */
|
||||
if (info->cch <= len + 1)
|
||||
info->cch--;
|
||||
else
|
||||
info->cch = len;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* return length of string, not on Win9x/ME if fType & MFT_BITMAP */
|
||||
info->cch = len;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (info->fMask & MIIM_FTYPE) info->fType = item->fType & MENUITEMINFO_TYPE_MASK;
|
||||
if (info->fMask & MIIM_BITMAP) info->hbmpItem = item->hbmpItem;
|
||||
if (info->fMask & MIIM_STATE) info->fState = item->fState & MENUITEMINFO_STATE_MASK;
|
||||
if (info->fMask & MIIM_ID) info->wID = item->wID;
|
||||
if (info->fMask & MIIM_DATA) info->dwItemData = item->dwItemData;
|
||||
|
||||
if (info->fMask & MIIM_SUBMENU) info->hSubMenu = item->hSubMenu;
|
||||
else info->hSubMenu = 0; /* hSubMenu is always cleared (not on Win9x/ME ) */
|
||||
|
||||
if (info->fMask & MIIM_CHECKMARKS)
|
||||
{
|
||||
info->hbmpChecked = item->hCheckBit;
|
||||
info->hbmpUnchecked = item->hUnCheckBit;
|
||||
}
|
||||
|
||||
release_menu_ptr( menu );
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/**********************************************************************
|
||||
* NtUserThunkedMenuItemInfo (win32u.@)
|
||||
*/
|
||||
|
@ -1004,6 +1121,12 @@ UINT WINAPI NtUserThunkedMenuItemInfo( HMENU handle, UINT pos, UINT flags, UINT
|
|||
|
||||
switch (method)
|
||||
{
|
||||
case NtUserGetMenuItemInfoA:
|
||||
return get_menu_item_info( handle, pos, flags, info, TRUE );
|
||||
|
||||
case NtUserGetMenuItemInfoW:
|
||||
return get_menu_item_info( handle, pos, flags, info, FALSE );
|
||||
|
||||
case NtUserInsertMenuItem:
|
||||
if (!info || info->cbSize != sizeof(*info))
|
||||
{
|
||||
|
|
|
@ -224,6 +224,8 @@ enum
|
|||
NtUserSetMenuItemInfo,
|
||||
NtUserInsertMenuItem,
|
||||
/* Wine extensions */
|
||||
NtUserGetMenuItemInfoA,
|
||||
NtUserGetMenuItemInfoW,
|
||||
NtUserGetMenuState,
|
||||
};
|
||||
|
||||
|
|
Loading…
Reference in a new issue