user32: When all items in a menu have either a bitmap or text but not both, then texts should be aligned with the bitmaps.

This commit is contained in:
Rein Klazes 2009-07-27 08:20:58 +02:00 committed by Alexandre Julliard
parent ea96cd3a52
commit c18cd1b46f
2 changed files with 119 additions and 9 deletions

View File

@ -112,7 +112,7 @@ typedef struct {
DWORD dwContextHelpID;
DWORD dwMenuData; /* application defined value */
HMENU hSysMenuOwner; /* Handle to the dummy sys menu holder */
SIZE maxBmpSize; /* Maximum size of the bitmap items */
WORD textOffset; /* Offset of text when items have both bitmaps and text */
} POPUPMENU, *LPPOPUPMENU;
/* internal flags for menu tracking */
@ -1071,8 +1071,7 @@ static void MENU_CalcItemSize( HDC hdc, MENUITEM *lpitem, HWND hwndOwner,
/* Keep the size of the bitmap in callback mode to be able
* to draw it correctly */
lpitem->bmpsize = size;
lppop->maxBmpSize.cx = max( lppop->maxBmpSize.cx, size.cx);
lppop->maxBmpSize.cy = max( lppop->maxBmpSize.cy, size.cy);
lppop->textOffset = max( lppop->textOffset, size.cx);
lpitem->rect.right += size.cx + 2;
itemheight = size.cy + 2;
}
@ -1166,6 +1165,7 @@ static void MENU_PopupMenuCalcSize( LPPOPUPMENU lppop )
MENUITEM *lpitem;
HDC hdc;
UINT start, i;
int textandbmp = FALSE;
int orgX, orgY, maxX, maxTab, maxTabWidth, maxHeight;
lppop->Width = lppop->Height = 0;
@ -1177,8 +1177,7 @@ static void MENU_PopupMenuCalcSize( LPPOPUPMENU lppop )
start = 0;
maxX = 2 + 1;
lppop->maxBmpSize.cx = 0;
lppop->maxBmpSize.cy = 0;
lppop->textOffset = 0;
while (start < lppop->nItems)
{
@ -1203,6 +1202,7 @@ static void MENU_PopupMenuCalcSize( LPPOPUPMENU lppop )
maxTab = max( maxTab, lpitem->xTab );
maxTabWidth = max(maxTabWidth,lpitem->rect.right-lpitem->xTab);
}
if( lpitem->text && lpitem->hbmpItem) textandbmp = TRUE;
}
/* Finish the column (set all items to the largest width found) */
@ -1218,6 +1218,12 @@ static void MENU_PopupMenuCalcSize( LPPOPUPMENU lppop )
}
lppop->Width = maxX;
/* if none of the items have both text and bitmap then
* the text and bitmaps are all aligned on the left. If there is at
* least one item with both text and bitmap then bitmaps are
* on the left and texts left aligned with the right hand side
* of the bitmaps */
if( !textandbmp) lppop->textOffset = 0;
/* space for 3d border */
lppop->Height += MENU_BOTTOM_MARGIN;
@ -1264,8 +1270,7 @@ static void MENU_MenuBarCalcSize( HDC hdc, LPRECT lprect,
maxY = lprect->top+1;
start = 0;
helpPos = ~0U;
lppop->maxBmpSize.cx = 0;
lppop->maxBmpSize.cy = 0;
lppop->textOffset = 0;
while (start < lppop->nItems)
{
lpitem = &lppop->items[start];
@ -1658,7 +1663,7 @@ static void MENU_DrawMenuItem( HWND hwnd, HMENU hmenu, HWND hwndOwner, HDC hdc,
DT_LEFT | DT_VCENTER | DT_SINGLELINE;
if( !(menu->dwStyle & MNS_CHECKORBMP))
rect.left += menu->maxBmpSize.cx;
rect.left += menu->textOffset;
if ( lpitem->fState & MFS_DEFAULT )
{
@ -1760,6 +1765,7 @@ static void MENU_DrawPopupMenu( HWND hwnd, HDC hdc, HMENU hmenu )
if( (menu = MENU_GetMenu( hmenu )))
{
TRACE("hmenu %p Style %08x\n", hmenu, menu->dwStyle);
/* draw menu items */
if( menu->nItems)
{

View File

@ -536,7 +536,7 @@ static void test_mbs_help( int ispop, int hassub, int mnuopt,
mi.cbSize = sizeof(mi);
mi.fMask = MIM_STYLE;
pGetMenuInfo( hmenu, &mi);
mi.dwStyle |= mnuopt == 1 ? MNS_NOCHECK : MNS_CHECKORBMP;
if( mnuopt) mi.dwStyle |= mnuopt == 1 ? MNS_NOCHECK : MNS_CHECKORBMP;
ret = pSetMenuInfo( hmenu, &mi);
ok( ret, "SetMenuInfo failed with error %d\n", GetLastError());
}
@ -3067,6 +3067,109 @@ static void test_menu_circref(void)
DestroyMenu( menu1);
}
/* test how the menu texts are aligned when the menu items have
* different combinations of text and bitmaps (bug #13350) */
static void test_menualign(void)
{
BYTE bmfill[300];
HMENU menu;
HBITMAP hbm1, hbm2, hbm3;
MENUITEMINFO mii = { sizeof(MENUITEMINFO)};
DWORD ret;
HWND hwnd;
MENUINFO mi = { sizeof( MENUINFO)};
if( !winetest_interactive) {
skip( "interactive alignment tests.\n");
return;
}
hwnd = CreateWindowEx(0,
"STATIC",
"Menu text alignment Test\nPlease make a selection.",
WS_OVERLAPPEDWINDOW,
100, 100,
300, 300,
NULL, NULL, 0, NULL);
ShowWindow( hwnd, SW_SHOW);
/* create bitmaps */
memset( bmfill, 0xcc, sizeof( bmfill));
hbm1 = CreateBitmap( 10,10,1,1,bmfill);
hbm2 = CreateBitmap( 20,20,1,1,bmfill);
hbm3 = CreateBitmap( 50,6,1,1,bmfill);
ok( hbm1 && hbm2 && hbm3, "Creating bitmaps failed\n");
menu = CreatePopupMenu();
ok( menu != NULL, "CreatePopupMenu() failed\n");
if( pGetMenuInfo) {
mi.fMask = MIM_STYLE;
ret = pGetMenuInfo( menu, &mi);
ok( menu != NULL, "GetMenuInfo() failed\n");
ok( 0 == mi.dwStyle, "menuinfo style is %x\n", mi.dwStyle);
}
/* test 1 */
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_ID;
mii.wID = 1;
mii.hbmpItem = hbm1;
mii.dwTypeData = (LPSTR) " OK: menu texts are correctly left-aligned.";
ret = InsertMenuItem( menu, -1, TRUE, &mii);
ok( ret, "InsertMenuItem() failed\n");
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_ID ;
mii.wID = 2;
mii.hbmpItem = hbm2;
mii.dwTypeData = (LPSTR) " FAIL: menu texts are NOT left-aligned.";
ret = InsertMenuItem( menu, -1, TRUE, &mii);
ok( ret, "InsertMenuItem() failed\n");
ret = TrackPopupMenu( menu, TPM_RETURNCMD, 110, 200, 0, hwnd, NULL);
ok( ret != 2, "User indicated that menu text alignment test 1 failed %d\n", ret);
/* test 2*/
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_ID;
mii.wID = 3;
mii.hbmpItem = hbm3;
mii.dwTypeData = NULL;
ret = InsertMenuItem( menu, 0, TRUE, &mii);
ok( ret, "InsertMenuItem() failed\n");
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_ID;
mii.wID = 1;
mii.hbmpItem = hbm1;
/* make the text a bit longer, to keep it readable */
/* this bug is on winXP and reproduced on wine */
mii.dwTypeData = (LPSTR) " OK: menu texts are to the right of the bitmaps........";
ret = SetMenuItemInfo( menu, 1, TRUE, &mii);
ok( ret, "SetMenuItemInfo() failed\n");
mii.wID = 2;
mii.hbmpItem = hbm2;
mii.dwTypeData = (LPSTR) " FAIL: menu texts are below the first bitmap. ";
ret = SetMenuItemInfo( menu, 2, TRUE, &mii);
ok( ret, "SetMenuItemInfo() failed\n");
ret = TrackPopupMenu( menu, TPM_RETURNCMD, 110, 200, 0, hwnd, NULL);
ok( ret != 2, "User indicated that menu text alignment test 2 failed %d\n", ret);
/* test 3 */
mii.fMask = MIIM_TYPE | MIIM_ID;
mii.wID = 3;
mii.fType = MFT_BITMAP;
mii.dwTypeData = (LPSTR) hbm3;
ret = SetMenuItemInfo( menu, 0, TRUE, &mii);
ok( ret, "SetMenuItemInfo() failed\n");
mii.fMask = MIIM_BITMAP | MIIM_STRING | MIIM_ID;
mii.wID = 1;
mii.hbmpItem = NULL;
mii.dwTypeData = (LPSTR) " OK: menu texts are below the bitmap.";
ret = SetMenuItemInfo( menu, 1, TRUE, &mii);
ok( ret, "SetMenuItemInfo() failed\n");
mii.wID = 2;
mii.hbmpItem = NULL;
mii.dwTypeData = (LPSTR) " FAIL: menu texts are NOT below the bitmap.";
ret = SetMenuItemInfo( menu, 2, TRUE, &mii);
ok( ret, "SetMenuItemInfo() failed\n");
ret = TrackPopupMenu( menu, TPM_RETURNCMD, 110, 200, 0, hwnd, NULL);
ok( ret != 2, "User indicated that menu text alignment test 3 failed %d\n", ret);
/* cleanup */
DeleteObject( hbm1);
DeleteObject( hbm2);
DeleteObject( hbm3);
DestroyMenu( menu);
DestroyWindow( hwnd);
}
START_TEST(menu)
{
init_function_pointers();
@ -3082,6 +3185,7 @@ START_TEST(menu)
test_CheckMenuRadioItem();
test_menu_resource_layout();
test_InsertMenu();
test_menualign();
}
register_menu_check_class();