diff --git a/include/extern.h b/include/extern.h index e59f3053a..8d6e5d483 100644 --- a/include/extern.h +++ b/include/extern.h @@ -1,4 +1,4 @@ -/* NetHack 3.6 extern.h $NHDT-Date: 1550524545 2019/02/18 21:15:45 $ $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.694 $ */ +/* NetHack 3.6 extern.h $NHDT-Date: 1552945074 2019/03/18 21:37:54 $ $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.695 $ */ /* Copyright (c) Steve Creps, 1988. */ /* NetHack may be freely redistributed. See license for details. */ @@ -1177,7 +1177,7 @@ E boolean FDECL(usmellmon, (struct permonst *)); E int FDECL(mapglyph, (int, int *, int *, unsigned *, int, int)); E char *FDECL(encglyph, (int)); -E const char *FDECL(decode_mixed, (char *,const char *)); +E char *FDECL(decode_mixed, (char *, const char *)); E void FDECL(genl_putmixed, (winid, int, const char *)); /* ### mcastu.c ### */ diff --git a/include/wincurs.h b/include/wincurs.h index 549ce9ae0..d4db5518b 100644 --- a/include/wincurs.h +++ b/include/wincurs.h @@ -114,6 +114,7 @@ extern void curses_end_screen(void); extern void curses_outrip(winid wid, int how); extern void genl_outrip(winid tmpwin, int how, time_t when); extern void curses_preference_update(const char *pref); +extern void curs_reset_windows(boolean, boolean); /* curswins.c */ diff --git a/src/mapglyph.c b/src/mapglyph.c index 856b898e3..960bb3287 100644 --- a/src/mapglyph.c +++ b/src/mapglyph.c @@ -1,4 +1,4 @@ -/* NetHack 3.6 mapglyph.c $NHDT-Date: 1526429201 2018/05/16 00:06:41 $ $NHDT-Branch: NetHack-3.6.0 $:$NHDT-Revision: 1.47 $ */ +/* NetHack 3.6 mapglyph.c $NHDT-Date: 1552945095 2019/03/18 21:38:15 $ $NHDT-Branch: NetHack-3.6.2-beta01 $:$NHDT-Revision: 1.48 $ */ /* Copyright (c) David Cohrs, 1991 */ /* NetHack may be freely redistributed. See license for details. */ @@ -249,7 +249,7 @@ int glyph; return encbuf; } -const char * +char * decode_mixed(buf, str) char *buf; const char *str; @@ -257,8 +257,8 @@ const char *str; static const char hex[] = "00112233445566778899aAbBcCdDeEfF"; char *put = buf; - if (!put || !str) - return ""; + if (!str) + return strcpy(buf, ""); while (*str) { if (*str == '\\') { diff --git a/win/curses/cursinit.c b/win/curses/cursinit.c index 8abe6b592..7f2a4f84f 100644 --- a/win/curses/cursinit.c +++ b/win/curses/cursinit.c @@ -134,7 +134,6 @@ curses_create_main_windows() borders = FALSE; } - if (borders) { border_space = 2; hspace -= border_space; @@ -145,35 +144,44 @@ curses_create_main_windows() } /* Determine status window orientation */ - if (!iflags.wc_align_status || (iflags.wc_align_status == ALIGN_TOP) - || (iflags.wc_align_status == ALIGN_BOTTOM)) { - if (!iflags.wc_align_status) { - iflags.wc_align_status = ALIGN_BOTTOM; - } + if (!iflags.wc_align_status) + iflags.wc_align_status = ALIGN_BOTTOM; + if (iflags.wc_align_status == ALIGN_TOP + || iflags.wc_align_status == ALIGN_BOTTOM) { status_orientation = iflags.wc_align_status; - } else { /* left or right alignment */ - - /* Max space for player name and title horizontally */ - if ((hspace >= 26) && (term_rows >= 24)) { + } else { /* left or right alignment */ + /* + * Max space for player name and title horizontally. + * [Width of 26 gives enough room for a 24 character + * hitpoint bar (horizontal layout uses 30 for that) and + * can accommodate widest field ("Experience : 30/123456789") + * other than title without truncating anything. + * Height originally required at least 24 lines, but 21 + * suffices and 20 can be made to work by suppressing score.] + */ + if (hspace >= 26 && term_rows >= 20) { status_orientation = iflags.wc_align_status; hspace -= (26 + border_space); } else { + /* orientation won't match option setting, making 'O' command's + list of settings seem inaccurate; but leaving the requested + setting in iflags might allow it to take effect if the main + window gets resized */ status_orientation = ALIGN_BOTTOM; } } /* Determine message window orientation */ - if (!iflags.wc_align_message || (iflags.wc_align_message == ALIGN_TOP) - || (iflags.wc_align_message == ALIGN_BOTTOM)) { - if (!iflags.wc_align_message) { - iflags.wc_align_message = ALIGN_TOP; - } + if (!iflags.wc_align_message) + iflags.wc_align_message = ALIGN_TOP; + if (iflags.wc_align_message == ALIGN_TOP + || iflags.wc_align_message == ALIGN_BOTTOM) { message_orientation = iflags.wc_align_message; - } else { /* left or right alignment */ - + } else { /* left or right alignment */ if ((hspace - border_space) >= 25) { /* Arbitrary */ message_orientation = iflags.wc_align_message; } else { + /* orientation won't match option setting (see above) */ message_orientation = ALIGN_TOP; } } @@ -192,7 +200,6 @@ curses_create_main_windows() int inv_y = 0; int map_x = 0; int map_y = 0; - int message_height = 0; int message_width = 0; int status_height = 0; @@ -201,20 +208,11 @@ curses_create_main_windows() int inv_width = 0; int map_height = (term_rows - border_space); int map_width = (term_cols - border_space); - int statusheight = 3; - - boolean status_vertical = FALSE; - boolean msg_vertical = FALSE; - - if (status_orientation == ALIGN_LEFT || - status_orientation == ALIGN_RIGHT) - status_vertical = TRUE; - if (message_orientation == ALIGN_LEFT || - message_orientation == ALIGN_RIGHT) - msg_vertical = TRUE; - - if (iflags.statuslines < 3) - statusheight = 2; + int statusheight = (iflags.statuslines < 3) ? 2 : 3; + boolean status_vertical = (status_orientation == ALIGN_LEFT + || status_orientation == ALIGN_RIGHT); + boolean msg_vertical = (message_orientation == ALIGN_LEFT + || message_orientation == ALIGN_RIGHT); /* Vertical windows have priority. Otherwise, priotity is: status > inv > msg */ @@ -227,9 +225,7 @@ curses_create_main_windows() if (iflags.perm_invent) { /* Take up all width unless msgbar is also vertical. */ - int width = -25; - if (msg_vertical) - width = 25; + int width = msg_vertical ? 25 : -25; set_window_position(&inv_x, &inv_y, &inv_width, &inv_height, ALIGN_RIGHT, &map_x, &map_y, @@ -261,7 +257,6 @@ curses_create_main_windows() if (map_width > COLNO) map_width = COLNO; - if (map_height > ROWNO) map_height = ROWNO; @@ -270,7 +265,6 @@ curses_create_main_windows() curses_del_nhwin(MESSAGE_WIN); curses_del_nhwin(MAP_WIN); curses_del_nhwin(INV_WIN); - clear(); } diff --git a/win/curses/cursinvt.c b/win/curses/cursinvt.c index b96037e01..17af0381b 100644 --- a/win/curses/cursinvt.c +++ b/win/curses/cursinvt.c @@ -23,9 +23,13 @@ curses_update_inv(void) /* It's not. Re-initialize the main windows if the option was enabled. */ if (iflags.perm_invent) { - curses_create_main_windows(); - curses_last_messages(); - doredraw(); + /* [core_]status_initialize, curses_create_main_windows, + curses_last_messages, [core_]doredraw; doredraw will + call (*update_inventory) [curses_update_inventory] which + will call us but 'win' should be defined that time */ + curs_reset_windows(TRUE, FALSE); + /* TODO: guard against window creation failure [if that's + possible] which would lead to uncontrolled recursion */ } return; } diff --git a/win/curses/cursmain.c b/win/curses/cursmain.c index 1791791a0..efeda3bcd 100644 --- a/win/curses/cursmain.c +++ b/win/curses/cursmain.c @@ -210,13 +210,12 @@ curses_askname() void curses_get_nh_event() { + boolean do_reset = FALSE; + #ifdef PDCURSES if (is_termresized()) { resize_term(0, 0); - getmaxyx(base_term, term_rows, term_cols); - curses_create_main_windows(); - curses_last_messages(); - doredraw(); + do_reset = TRUE; } #endif #ifdef NCURSES_VERSION /* Is there a better way to detect ncurses? */ @@ -224,14 +223,16 @@ curses_get_nh_event() if (!isendwin()) { endwin(); } - refresh(); - getmaxyx(base_term, term_rows, term_cols); - curses_create_main_windows(); - curses_last_messages(); - doredraw(); + do_reset = TRUE; } #endif + + if (do_reset) { + getmaxyx(base_term, term_rows, term_cols); + /* status_initialize, create_main_windows, last_messages, doredraw */ + curs_reset_windows(TRUE, TRUE); + } } /* Exits the window system. This should dismiss all windows, @@ -526,9 +527,7 @@ curses_update_inventory(void) changed the option. */ if (!iflags.perm_invent) { if (curses_get_nhwin(INV_WIN)) { - curses_create_main_windows(); - curses_last_messages(); - doredraw(); + curs_reset_windows(TRUE, FALSE); } return; } @@ -850,14 +849,38 @@ preference_update(preference) void curses_preference_update(const char *pref) { - if (!strcmp(pref, "hilite_status") || !strcmp(pref, "align_status")) - status_initialize(REASSESS_ONLY); + boolean redo_main = FALSE, redo_status = FALSE; if (!strcmp(pref, "align_status") - || !strcmp(pref, "align_message")) { + || !strcmp(pref, "statuslines") + || !strcmp(pref, "windowborders")) + redo_main = redo_status = TRUE; + else if (!strcmp(pref, "hilite_status")) + redo_status = TRUE; + else if (!strcmp(pref, "align_message")) + redo_main = TRUE; + + if (redo_main || redo_status) + curs_reset_windows(redo_main, redo_status); +} + +void +curs_reset_windows(boolean redo_main, boolean redo_status) +{ + boolean need_redraw = FALSE; + + if (redo_status) { + status_initialize(REASSESS_ONLY); + need_redraw = TRUE; + } + if (redo_main) { curses_create_main_windows(); + need_redraw = TRUE; + } + if (need_redraw) { curses_last_messages(); doredraw(); } } +/*cursmain.c*/ diff --git a/win/curses/curswins.c b/win/curses/curswins.c index 3cd84190d..4db35e144 100644 --- a/win/curses/curswins.c +++ b/win/curses/curswins.c @@ -490,9 +490,6 @@ curses_puts(winid wid, int attr, const char *text) #if 0 if (wid == STATUS_WIN) { curses_update_stats(); /* We will do the write ourselves */ - /* Inventory updating isn't performed on redraws, so - also update inventory here... */ - curses_update_inventory(); return; } #endif