Implement three line status

This commit is contained in:
Ray Chason
2026-08-10 09:28:04 +03:00
committed by Pasi Kallinen
parent 7521e7120a
commit b763944fb4
2 changed files with 110 additions and 62 deletions
+1
View File
@@ -135,6 +135,7 @@ struct window_procs X11_procs = {
#ifdef STATUS_HILITES #ifdef STATUS_HILITES
| WC2_RESET_STATUS | WC2_HILITE_STATUS | WC2_RESET_STATUS | WC2_HILITE_STATUS
#endif #endif
| WC2_EXTRASTATUS
| WC2_MENU_SHIFT ), | WC2_MENU_SHIFT ),
{1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}, /* color availability */ {1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}, /* color availability */
X11_init_nhwindows, X11_init_nhwindows,
+109 -62
View File
@@ -124,7 +124,8 @@ static void adjust_status_tty(struct xwindow *, const char *);
static void tty_status_exposed(Widget, XtPointer, XtPointer); static void tty_status_exposed(Widget, XtPointer, XtPointer);
static void tty_status_blink(XtPointer client_data, XtIntervalId *timer); static void tty_status_blink(XtPointer client_data, XtIntervalId *timer);
static void tty_status_redraw(Widget); static void tty_status_redraw(Widget);
static int tty_render_text(Widget, int, int, const char *, int, int, boolean); static int tty_render_field(Widget, int, int, enum statusfields);
static int tty_render_text(Widget, int, int, const char *, int, int, enum statusfields);
extern const char *status_fieldfmt[MAXBLSTATS]; extern const char *status_fieldfmt[MAXBLSTATS];
extern char *status_vals[MAXBLSTATS]; extern char *status_vals[MAXBLSTATS];
@@ -141,17 +142,22 @@ static int hpbar_percent, hpbar_color;
static int next_cond_indx = 0, prev_cond_indx = 0; static int next_cond_indx = 0, prev_cond_indx = 0;
#endif /*RLC*/ #endif /*RLC*/
/* TODO: support statuslines:3 in addition to 2 for the tty-style status */ static enum statusfields X11_fieldorder_2[][18] = {
#define X11_NUM_STATUS_LINES 2
#define X11_NUM_STATUS_FIELD 16
static enum statusfields X11_fieldorder[][X11_NUM_STATUS_FIELD] = {
{ BL_TITLE, BL_STR, BL_DX, BL_CO, BL_IN, BL_WI, BL_CH, BL_ALIGN, { BL_TITLE, BL_STR, BL_DX, BL_CO, BL_IN, BL_WI, BL_CH, BL_ALIGN,
BL_SCORE, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_SCORE, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_FLUSH,
BL_FLUSH, BL_FLUSH }, BL_FLUSH, BL_FLUSH, BL_FLUSH, BL_FLUSH },
{ BL_LEVELDESC, BL_GOLD, BL_HP, BL_HPMAX, BL_ENE, BL_ENEMAX, { BL_LEVELDESC, BL_GOLD, BL_HP, BL_HPMAX, BL_ENE, BL_ENEMAX,
BL_AC, BL_XP, BL_EXP, BL_HD, BL_TIME, BL_HUNGER, BL_AC, BL_XP, BL_EXP, BL_HD, BL_TIME, BL_HUNGER, BL_CAP,
BL_CAP, BL_CONDITION, BL_VERS, BL_FLUSH } BL_CONDITION, BL_WEAPON, BL_ARMOR, BL_TERRAIN, BL_VERS }
};
static enum statusfields X11_fieldorder_3[][13] = {
{ BL_TITLE, BL_STR, BL_DX, BL_CO, BL_IN, BL_WI, BL_CH, BL_SCORE, BL_FLUSH },
{ BL_ALIGN, BL_GOLD, BL_HP, BL_HPMAX, BL_ENE, BL_ENEMAX,
BL_AC, BL_XP, BL_EXP, BL_HD, BL_HUNGER, BL_CAP,
BL_FLUSH },
{ BL_LEVELDESC, BL_TIME, BL_CONDITION, BL_WEAPON, BL_ARMOR, BL_TERRAIN,
BL_VERS, BL_FLUSH }
}; };
/* condition list for tty-style display, roughly in order of importance */ /* condition list for tty-style display, roughly in order of importance */
@@ -1194,6 +1200,50 @@ tty_status_blink(XtPointer client_data, XtIntervalId *timer)
static void static void
tty_status_redraw(Widget w) tty_status_redraw(Widget w)
{
Arg args[5];
int num_args;
Dimension width;
/* Get the height of the font and the width of the widget */
num_args = 0;
XtSetArg(args[num_args], XtNwidth, &width); num_args++;
XtGetValues(w, args, num_args);
int height = nhFontHeight(w);
int x = 0;
int y = 0;
XClearWindow(XtDisplay(w), XtWindow(w));
if (iflags.wc2_statuslines <= 2) {
for (unsigned row = 0; row < SIZE(X11_fieldorder_2); ++row) {
for (unsigned i = 0; i < SIZE(X11_fieldorder_2[0]); ++i) {
enum statusfields fld = X11_fieldorder_2[row][i];
if (fld == BL_FLUSH) {
break;
}
x += tty_render_field(w, x, y, fld);
}
x = 0;
y += height;
}
} else {
for (unsigned row = 0; row < SIZE(X11_fieldorder_3); ++row) {
for (unsigned i = 0; i < SIZE(X11_fieldorder_3[0]); ++i) {
enum statusfields fld = X11_fieldorder_3[row][i];
if (fld == BL_FLUSH) {
break;
}
x += tty_render_field(w, x, y, fld);
}
x = 0;
y += height;
}
}
}
/* Render one field of the TTY status */
static int
tty_render_field(Widget w, int x, int y, enum statusfields fld)
{ {
static struct stat_fmt { static struct stat_fmt {
const char *pre; const char *pre;
@@ -1222,71 +1272,56 @@ tty_status_redraw(Widget w)
[BL_LEVELDESC] = { NULL, NULL }, [BL_LEVELDESC] = { NULL, NULL },
[BL_EXP] = { "/", NULL }, [BL_EXP] = { "/", NULL },
[BL_CONDITION] = { NULL, NULL }, [BL_CONDITION] = { NULL, NULL },
[BL_WEAPON] = { NULL, NULL }, /* not in 2-line */ [BL_WEAPON] = { NULL, NULL },
[BL_ARMOR] = { NULL, NULL }, /* not in 2-line */ [BL_ARMOR] = { NULL, NULL },
[BL_TERRAIN] = { NULL, NULL }, /* not in 2-line */ [BL_TERRAIN] = { NULL, NULL },
[BL_VERS] = { NULL, NULL }, [BL_VERS] = { NULL, NULL },
}; };
Arg args[5];
int num_args;
Dimension width;
/* Get the height of the font and the width of the widget */ int width = 0;
num_args = 0;
XtSetArg(args[num_args], XtNwidth, &width); num_args++;
XtGetValues(w, args, num_args);
int height = nhFontHeight(w);
int x = 0; switch (fld) {
int y = 0; case BL_FLUSH:
XClearWindow(XtDisplay(w), XtWindow(w)); break;
for (unsigned row = 0; row < X11_NUM_STATUS_LINES; ++row) {
for (unsigned i = 0; i < X11_NUM_STATUS_FIELD; ++i) {
enum statusfields fld = X11_fieldorder[row][i];
switch (fld) {
case BL_FLUSH:
break;
case BL_CONDITION: case BL_CONDITION:
for (unsigned j = 0; j < SIZE(X11_cond_labels); ++j) { for (unsigned j = 0; j < SIZE(X11_cond_labels); ++j) {
struct tty_cond_field const *fldp = &X11_cond_labels[j]; struct tty_cond_field const *fldp = &X11_cond_labels[j];
if (fldp->text != NULL) { if (fldp->text != NULL) {
x += tty_render_text(w, x, y, " ", NO_COLOR, 0, FALSE); width += tty_render_text(w, x + width, y, " ", NO_COLOR, 0, BL_FLUSH);
x += tty_render_text(w, x, y, fldp->text, fldp->color, fldp->attrs, FALSE); width += tty_render_text(w, x + width, y, fldp->text, fldp->color, fldp->attrs, BL_FLUSH);
}
}
break;
default:
{
struct tty_status_field const *fldp = &X11_status_labels[fld];
if (fldp->text != NULL && fldp->text[0] != '\0') {
if (x != 0 && (formats[fld].pre == NULL || strchr("(/", formats[fld].pre[0]) == NULL)) {
x += tty_render_text(w, x, y, " ", NO_COLOR, 0, FALSE);
}
if (formats[fld].pre != NULL) {
x += tty_render_text(w, x, y, formats[fld].pre, NO_COLOR, 0, FALSE);
}
x += tty_render_text(w, x, y, fldp->text, fldp->color,
fldp->attrs, fld == BL_GOLD);
if (formats[fld].post != NULL) {
x += tty_render_text(w, x, y, formats[fld].post, NO_COLOR, 0, FALSE);
}
/* @@@TODO: do the percent field */
}
}
break;
} }
} }
x = 0; break;
y += height;
default:
{
struct tty_status_field const *fldp = &X11_status_labels[fld];
if (fldp->text != NULL && fldp->text[0] != '\0') {
if (x != 0 && (formats[fld].pre == NULL || strchr("(/", formats[fld].pre[0]) == NULL)) {
width += tty_render_text(w, x + width, y, " ", NO_COLOR, 0, BL_FLUSH);
}
if (formats[fld].pre != NULL) {
width += tty_render_text(w, x + width, y, formats[fld].pre, NO_COLOR, 0, BL_FLUSH);
}
width += tty_render_text(w, x + width, y, fldp->text, fldp->color,
fldp->attrs, fld);
if (formats[fld].post != NULL) {
width += tty_render_text(w, x + width, y, formats[fld].post, NO_COLOR, 0, BL_FLUSH);
}
/* @@@TODO: do the percent field */
}
}
break;
} }
return width;
} }
/* Render text as part of the TTY status */ /* Render text as part of the TTY status */
static int static int
tty_render_text(Widget w, int x, int y, const char *text, int color, int attr, tty_render_text(Widget w, int x, int y, const char *text, int color, int attr,
boolean is_gold) enum statusfields fld)
{ {
Arg args[5]; Arg args[5];
Cardinal num_args; Cardinal num_args;
@@ -1360,7 +1395,7 @@ tty_render_text(Widget w, int x, int y, const char *text, int color, int attr,
/* Gold will begin with a glyph string. Convert this to the proper /* Gold will begin with a glyph string. Convert this to the proper
character, which might possibly be Unicode */ character, which might possibly be Unicode */
if (is_gold && memcmp(text, "\\G", 2) == 0) { if (fld == BL_GOLD && memcmp(text, "\\G", 2) == 0) {
char *end; char *end;
unsigned long glyphcode = strtoul(text+2, &end, 16); unsigned long glyphcode = strtoul(text+2, &end, 16);
if ((glyphcode >> 16) == (unsigned) svc.context.rndencode && *end == ':') { if ((glyphcode >> 16) == (unsigned) svc.context.rndencode && *end == ':') {
@@ -1416,6 +1451,18 @@ tty_render_text(Widget w, int x, int y, const char *text, int color, int attr,
/* Get the width of the rendered string */ /* Get the width of the rendered string */
int width = XTextWidth(font, text, strlen(text)) + goldwidth; int width = XTextWidth(font, text, strlen(text)) + goldwidth;
/* Place version on the right */
if (fld == BL_VERS) {
num_args = 0;
Dimension wwidth;
XtSetArg(args[num_args], XtNwidth, &wwidth); num_args++;
XtGetValues(w, args, num_args);
int x2 = wwidth - width;
if (x2 > x) {
x = x2;
}
}
/* Render the string */ /* Render the string */
XDrawImageString(XtDisplay(w), XtWindow(w), ggc, XDrawImageString(XtDisplay(w), XtWindow(w), ggc,
x + goldwidth, y + font->max_bounds.ascent, x + goldwidth, y + font->max_bounds.ascent,