From ee7064746fdceb8d16a380e478792da1935a25b4 Mon Sep 17 00:00:00 2001 From: "nethack.allison" Date: Sun, 9 Jan 2005 23:35:52 +0000 Subject: [PATCH] AltGr-4 and alternate tiles in menus - trunk only (from ) On Mon, 03 Jan 2005 12:04:29 +0000, wrote: > Dear NetHack win32 developers, > > This bug does not affect the win32 binaries that you distribute but it > does affect NetHack 3.4.3 if I build it from source. The difference may > be due to different compilers or whatever. I'm using mingw32-gcc v3.2 > > I don't quite understand what's going on (I never was much good at > win32 programming), but it appears that the WM_KEYDOWN message for > AltGr-4 is being translated into a WM_CHAR message with a wParam of > 128. I don't understand why that should be, but anyway. The problem > then occurs when NetHack casts wParam to char which, since char is > signed, gives -128. onListChar() then passes -128 to isdigit() which > causes the crash. The fix appears to be to simply drop the cast: Also > > Newsgroups: rec.games.roguelike.nethack > Subject: Changing tile set for item list? > Date: 1 Jan 2005 20:03:08 -0800 > > > I'm using the windows interface for Nethack 3.4, and I've successfully > changed the tileset used by changing defaults.nh. The only problem is, > the item list (i.e. The list that comes up when I press "i") still uses > the old tiles. Is there any way to change the list so it uses the new > tiles? I've searched the guidebook to no avail. I'm debating if it is > even possible. > > Thanks for the help, > -Zmann trunk patch: - menu: display custom tiles if map is not ASCII - menu: display '-'/'+'/'#' in place of a tile if map is ASCII - fix isdigit() crash on AltGr-4 with mingw It looks kinda weird with huge tiles (e.g. absurd96) but that could be just me. Comments/suggestions are welcome. - --- doc/fixes35.0 | 2 + win/win32/mhmain.c | 6 -- win/win32/mhmenu.c | 151 ++++++++++++++++++++++++++++++--------------- win/win32/winMS.h | 9 ++- 4 files changed, 110 insertions(+), 58 deletions(-) diff --git a/doc/fixes35.0 b/doc/fixes35.0 index 4dba3a675..9969ac538 100644 --- a/doc/fixes35.0 +++ b/doc/fixes35.0 @@ -86,6 +86,8 @@ win32gui: fixed copy/paste error in read registry settings function win32gui: improved calculation of the size of the menu window win32gui: made auto-arrange windows on/off option (it was reset automatically which was unintuitive and in some cases annoying +win32gui: fix a possible crash with AltGr-4 WM_KEYDOWN handling +win32gui: use whatever alternate tile set is loaded in the menus platforms that support hangup: SAFERHANGUP to avoid losing objects in transit between lists when hangup occurs, and also avoid cheats due to well-timed hangups to stop a long melee diff --git a/win/win32/mhmain.c b/win/win32/mhmain.c index 5295f78dd..d496f50f1 100644 --- a/win/win32/mhmain.c +++ b/win/win32/mhmain.c @@ -158,12 +158,6 @@ numpad[KEY_LAST][3] = { #define KEYTABLE_SHIFT(x) ((iflags.num_pad ? numpad : keypad)[x][1]) #define KEYTABLE(x) (STATEON(VK_SHIFT) ? KEYTABLE_SHIFT(x) : KEYTABLE_REGULAR(x)) -/* map mode macros */ -#define IS_MAP_FIT_TO_SCREEN(mode) ((mode)==MAP_MODE_ASCII_FIT_TO_SCREEN || \ - (mode)==MAP_MODE_TILES_FIT_TO_SCREEN ) - -#define IS_MAP_ASCII(mode) ((mode)!=MAP_MODE_TILES && (mode)!=MAP_MODE_TILES_FIT_TO_SCREEN) - static const char *extendedlist = "acdefijlmnopqrstuvw?2"; #define SCANLO 0x02 diff --git a/win/win32/mhmenu.c b/win/win32/mhmenu.c index c21d22ff9..464071589 100644 --- a/win/win32/mhmenu.c +++ b/win/win32/mhmenu.c @@ -72,6 +72,7 @@ static WNDPROC editControlWndProc = NULL; #define NHMENU_IS_SELECTABLE(item) ((item).identifier.a_obj!=NULL) #define NHMENU_IS_SELECTED(item) ((item).count!=0) +#define NHMENU_HAS_GLYPH(item) ((item).glyph!=NO_GLYPH) BOOL CALLBACK MenuWndProc(HWND, UINT, WPARAM, LPARAM); LRESULT CALLBACK NHMenuListWndProc(HWND, UINT, WPARAM, LPARAM); @@ -869,6 +870,7 @@ BOOL onMeasureItem(HWND hWnd, WPARAM wParam, LPARAM lParam) HDC hdc; PNHMenuWindow data; RECT list_rect; + int i; lpmis = (LPMEASUREITEMSTRUCT) lParam; data = (PNHMenuWindow)GetWindowLong(hWnd, GWL_USERDATA); @@ -878,8 +880,17 @@ BOOL onMeasureItem(HWND hWnd, WPARAM wParam, LPARAM lParam) saveFont = SelectObject(hdc, mswin_get_font(NHW_MENU, ATR_INVERSE, hdc, FALSE)); GetTextMetrics(hdc, &tm); - /* Set the height of the list box items. */ - lpmis->itemHeight = max(tm.tmHeight, TILE_Y)+2; + /* Set the height of the list box items to max height of the individual items */ + for( i=0; imenu.size; i++) { + if( NHMENU_HAS_GLYPH(data->menu.items[i]) && !IS_MAP_ASCII(iflags.wc_map_mode) ) { + lpmis->itemHeight = max( lpmis->itemHeight, (UINT)max(tm.tmHeight, GetNHApp()->mapTile_Y) ); + } else { + lpmis->itemHeight = max( lpmis->itemHeight, (UINT)max(tm.tmHeight, TILE_Y) ); + } + } + lpmis->itemHeight += 2; + + /* set width to the window width */ lpmis->itemWidth = list_rect.right - list_rect.left; SelectObject(hdc, saveFont); @@ -903,6 +914,7 @@ BOOL onDrawItem(HWND hWnd, WPARAM wParam, LPARAM lParam) COLORREF OldBg, OldFg, NewBg; char *p, *p1; int column; + int spacing = 0; lpdis = (LPDRAWITEMSTRUCT) lParam; @@ -921,31 +933,35 @@ BOOL onDrawItem(HWND hWnd, WPARAM wParam, LPARAM lParam) menu_fg_brush ? menu_fg_color : (COLORREF)GetSysColor(DEFAULT_COLOR_FG_MENU)); GetTextMetrics(lpdis->hDC, &tm); + spacing = tm.tmAveCharWidth; + /* set initial offset */ x = lpdis->rcItem.left + 1; /* print check mark and letter */ if( NHMENU_IS_SELECTABLE(*item) ) { - char buf[2]; - if (data->how != PICK_NONE) { - HGDIOBJ saveBrush; - HBRUSH hbrCheckMark; - - switch(item->count) { - case -1: hbrCheckMark = CreatePatternBrush(data->bmpChecked); break; - case 0: hbrCheckMark = CreatePatternBrush(data->bmpNotChecked); break; - default: hbrCheckMark = CreatePatternBrush(data->bmpCheckedCount); break; + char buf[2]; + if (data->how != PICK_NONE) { + HGDIOBJ saveBrush; + HBRUSH hbrCheckMark; + + switch(item->count) { + case -1: hbrCheckMark = CreatePatternBrush(data->bmpChecked); break; + case 0: hbrCheckMark = CreatePatternBrush(data->bmpNotChecked); break; + default: hbrCheckMark = CreatePatternBrush(data->bmpCheckedCount); break; + } + + y = (lpdis->rcItem.bottom + lpdis->rcItem.top - TILE_Y) / 2; + SetBrushOrgEx(lpdis->hDC, x, y, NULL); + saveBrush = SelectObject(lpdis->hDC, hbrCheckMark); + PatBlt(lpdis->hDC, x, y, TILE_X, TILE_Y, PATCOPY); + SelectObject(lpdis->hDC, saveBrush); + DeleteObject(hbrCheckMark); + } - y = (lpdis->rcItem.bottom + lpdis->rcItem.top - TILE_Y) / 2; - SetBrushOrgEx(lpdis->hDC, x, y, NULL); - saveBrush = SelectObject(lpdis->hDC, hbrCheckMark); - PatBlt(lpdis->hDC, x, y, TILE_X, TILE_Y, PATCOPY); - SelectObject(lpdis->hDC, saveBrush); - DeleteObject(hbrCheckMark); + x += TILE_X + spacing; - } - x += TILE_X + 5; if(item->accelerator!=0) { buf[0] = item->accelerator; buf[1] = '\x0'; @@ -953,32 +969,67 @@ BOOL onDrawItem(HWND hWnd, WPARAM wParam, LPARAM lParam) SetRect( &drawRect, x, lpdis->rcItem.top, lpdis->rcItem.right, lpdis->rcItem.bottom ); DrawText(lpdis->hDC, NH_A2W(buf, wbuf, 2), 1, &drawRect, DT_LEFT | DT_VCENTER | DT_SINGLELINE | DT_NOPREFIX); } - x += tm.tmAveCharWidth + tm.tmOverhang + 5; + x += tm.tmAveCharWidth + tm.tmOverhang + spacing; } else { - x += TILE_X + tm.tmAveCharWidth + tm.tmOverhang + 10; + x += TILE_X + tm.tmAveCharWidth + tm.tmOverhang + 2*spacing; } /* print glyph if present */ - if( item->glyph != NO_GLYPH ) { - HGDIOBJ saveBmp; - - saveBmp = SelectObject(tileDC, GetNHApp()->bmpTiles); - ntile = glyph2tile[ item->glyph ]; - t_x = (ntile % TILES_PER_LINE)*TILE_X; - t_y = (ntile / TILES_PER_LINE)*TILE_Y; - - y = (lpdis->rcItem.bottom + lpdis->rcItem.top - TILE_Y) / 2; + if( NHMENU_HAS_GLYPH(*item) ) { + if( !IS_MAP_ASCII(iflags.wc_map_mode) ) { + HGDIOBJ saveBmp; + + saveBmp = SelectObject(tileDC, GetNHApp()->bmpMapTiles); + ntile = glyph2tile[ item->glyph ]; + t_x = (ntile % GetNHApp()->mapTilesPerLine)*GetNHApp()->mapTile_X; + t_y = (ntile / GetNHApp()->mapTilesPerLine)*GetNHApp()->mapTile_Y; + + y = (lpdis->rcItem.bottom + lpdis->rcItem.top - GetNHApp()->mapTile_Y) / 2; + + if( GetNHApp()->bmpMapTiles == GetNHApp()->bmpTiles ) { + /* using original nethack tiles - apply image transparently */ + nhapply_image_transparent( + lpdis->hDC, x, y, TILE_X, TILE_Y, + tileDC, t_x, t_y, TILE_X, TILE_Y, TILE_BK_COLOR ); + } else { + /* using custom tiles - simple blt */ + BitBlt( + lpdis->hDC, x, y, GetNHApp()->mapTile_X, GetNHApp()->mapTile_Y, + tileDC, t_x, t_y, SRCCOPY ); + } + SelectObject(tileDC, saveBmp); + x += GetNHApp()->mapTile_X; + } else { + const char *sel_ind; + switch(item->count) { + case -1: sel_ind = "+"; break; + case 0: sel_ind = "-"; break; + default: sel_ind = "#"; break; + } - nhapply_image_transparent( - lpdis->hDC, x, y, TILE_X, TILE_Y, - tileDC, t_x, t_y, TILE_X, TILE_Y, TILE_BK_COLOR ); - SelectObject(tileDC, saveBmp); + SetRect( + &drawRect, + x, + lpdis->rcItem.top, + min(x + tm.tmAveCharWidth, lpdis->rcItem.right), + lpdis->rcItem.bottom + ); + DrawText(lpdis->hDC, + NH_A2W(sel_ind, wbuf, BUFSZ), + 1, + &drawRect, + DT_CENTER| DT_VCENTER | DT_SINGLELINE + ); + x += tm.tmAveCharWidth; + } + } else { + /* no glyph - need to adjust so help window won't look to cramped */ + x += TILE_X; } - x += TILE_X + 5; + x += spacing; /* draw item text */ - p1 = item->str; p = strchr(item->str, '\t'); column = 0; @@ -1446,27 +1497,23 @@ LRESULT CALLBACK NHMenuListWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARA { BOOL bUpdateFocusItem; + /* we will redraw focused item whenever horizontal scrolling occurs + since "Count: XXX" indicator is garbled by scrolling */ bUpdateFocusItem = FALSE; switch(message) { - - /* filter keyboard input for the control */ case WM_KEYDOWN: - case WM_KEYUP: { - MSG msg; - BOOL processed; - - processed = FALSE; - if( PeekMessage(&msg, hWnd, WM_CHAR, WM_CHAR, PM_REMOVE) ) { - if( onListChar(GetParent(hWnd), hWnd, (char)msg.wParam)==-2 ) { - processed = TRUE; - } - } - if( processed ) return 0; - if( wParam==VK_LEFT || wParam==VK_RIGHT ) bUpdateFocusItem = TRUE; - } break; + break; + + case WM_CHAR: /* filter keyboard input for the control */ + if( wParam>0 && wParam<256 && onListChar(GetParent(hWnd), hWnd, (char)wParam)==-2 ) { + return 0; + } else { + return 1; + } + break; case WM_SIZE: case WM_HSCROLL: @@ -1480,6 +1527,7 @@ LRESULT CALLBACK NHMenuListWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARA return FALSE; } + /* update focused item */ if( bUpdateFocusItem ) { int i; RECT rt; @@ -1492,6 +1540,7 @@ LRESULT CALLBACK NHMenuListWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARA } } + /* call ListView control window proc */ if( wndProcListViewOrig ) return CallWindowProc(wndProcListViewOrig, hWnd, message, wParam, lParam); else diff --git a/win/win32/winMS.h b/win/win32/winMS.h index 100499090..31282e396 100644 --- a/win/win32/winMS.h +++ b/win/win32/winMS.h @@ -217,5 +217,12 @@ extern COLORREF message_fg_color; #define NH_A2W(a, w, cb) (strncpy((w), (a), (cb))) #endif -#endif /* WINmswin_H */ +/* map mode macros */ +#define IS_MAP_FIT_TO_SCREEN(mode) ((mode)==MAP_MODE_ASCII_FIT_TO_SCREEN || \ + (mode)==MAP_MODE_TILES_FIT_TO_SCREEN ) + +#define IS_MAP_ASCII(mode) ((mode)!=MAP_MODE_TILES && (mode)!=MAP_MODE_TILES_FIT_TO_SCREEN) + + +#endif /* WINMS_H */ -- 2.50.1