Commit 577f7faf authored by Benno Schulenberg's avatar Benno Schulenberg
Browse files

screen: make better use of the available space in the titlebar

When the terminal is very narrow, there is little point in showing only
part of the version string -- and chewing off one or two digits from the
version number might even give someone a wrong idea.  The user is better
served with always showing the full filename, as long as it fits in the
available screen width.

This fixes https://savannah.gnu.org/bugs/?47703.
No related merge requests found
Showing with 78 additions and 121 deletions
+78 -121
...@@ -1915,27 +1915,18 @@ char *display_string(const char *buf, size_t start_col, size_t len, bool ...@@ -1915,27 +1915,18 @@ char *display_string(const char *buf, size_t start_col, size_t len, bool
* of path on the titlebar. */ * of path on the titlebar. */
void titlebar(const char *path) void titlebar(const char *path)
{ {
int space = COLS; size_t verlen, prefixlen, pathlen, statelen;
/* The space we have available for display. */ /* The width of the different titlebar elements, in columns. */
size_t verlen = strlenpt(BRANDING); size_t pluglen = 0;
/* The length of the version message in columns. */ /* The width that "Modified" would take up. */
const char *prefix; size_t offset = 0;
/* "DIR:", "File:", or "New Buffer". Goes before filename. */ /* The position at which the center part of the titlebar starts. */
size_t prefixlen; const char *prefix = "";
/* The length of the prefix in columns, plus one for padding. */ /* What is shown before the path -- "File:", "DIR:", or "". */
const char *state; const char *state = "";
/* "Modified", "View", or "". Shows the state of this /* The state of the current buffer -- "Modified", "View", or "". */
* buffer. */ char *fragment;
size_t statelen = 0; /* The tail part of the pathname when dottified. */
/* The length of the state in columns, or the length of
* "Modified" if the state is blank and we're not in the file
* browser. */
char *exppath = NULL;
/* The filename, expanded for display. */
bool newfie = FALSE;
/* Do we say "New Buffer"? */
bool dots = FALSE;
/* Do we put an ellipsis before the path? */
assert(path != NULL || openfile->filename != NULL); assert(path != NULL || openfile->filename != NULL);
...@@ -1945,123 +1936,89 @@ void titlebar(const char *path) ...@@ -1945,123 +1936,89 @@ void titlebar(const char *path)
blank_titlebar(); blank_titlebar();
/* Limit the length of the version message to a third of the width of /* Do as Pico: if there is not enough width available for all items,
* the screen, minus three columns for spaces. */ * first sacrifice the version string, then eat up the side spaces,
if (verlen > (COLS / 3) - 3) * then sacrifice the prefix, and only then start dottifying. */
verlen = (COLS / 3) - 3;
/* Leave two spaces before the version message, and account also
* for the space after it. */
mvwaddnstr(topwin, 0, 2, BRANDING, actual_x(BRANDING, verlen));
verlen += 3;
/* Account for the full length of the version message. */
space -= verlen;
/* Figure out the path, prefix and state strings. */
#ifndef DISABLE_BROWSER #ifndef DISABLE_BROWSER
/* Don't display the state if we're in the file browser. */
if (path != NULL)
state = "";
else
#endif
state = openfile->modified ? _("Modified") : ISSET(VIEW_MODE) ?
_("View") : "";
statelen = strlenpt((*state == '\0' && path == NULL) ?
_("Modified") : state);
/* If possible, add a space before state. */
if (space > 0 && statelen < space)
statelen++;
else
goto the_end;
#ifndef DISABLE_BROWSER
/* path should be a directory if we're in the file browser. */
if (path != NULL) if (path != NULL)
prefix = _("DIR:"); prefix = _("DIR:");
else else
#endif #endif
if (openfile->filename[0] == '\0') { {
prefix = _("New Buffer"); if (openfile->filename[0] == '\0')
newfie = TRUE; path = _("New Buffer");
} else else {
prefix = _("File:"); path = openfile->filename;
prefix = _("File:");
prefixlen = strnlenpt(prefix, space - statelen) + 1; }
/* If newfie is FALSE, add a space after prefix. */
if (!newfie && prefixlen + statelen < space)
prefixlen++;
/* If we're not in the file browser, set path to the current
* filename. */
if (path == NULL)
path = openfile->filename;
/* Account for the full lengths of the prefix and the state. */
if (space >= prefixlen + statelen)
space -= prefixlen + statelen;
else
space = 0;
/* space is now the room we have for the filename. */
if (!newfie) {
size_t lenpt = strlenpt(path), start_col;
/* Don't set dots to TRUE if we have fewer than eight columns if (openfile->modified)
* (i.e. one column for padding, plus seven columns for a state = _("Modified");
* filename). */ else if (ISSET(VIEW_MODE))
dots = (space >= 8 && lenpt >= space); state = _("View");
if (dots) { pluglen = strlenpt(_("Modified")) + 1;
start_col = lenpt - space + 3; }
space -= 3;
} else
start_col = 0;
exppath = display_string(path, start_col, space, FALSE); /* Determine the widths of the four elements, including their padding. */
verlen = strlenpt(BRANDING) + 3;
prefixlen = strlenpt(prefix);
if (prefixlen > 0)
prefixlen++;
pathlen= strlenpt(path);
statelen = strlenpt(state) + 2;
if (statelen > 2) {
pathlen++;
pluglen = 0;
} }
/* If dots is TRUE, we will display something like "File: /* Only print the version message when there is room for it. */
* ...ename". */ if (verlen + prefixlen + pathlen + pluglen + statelen <= COLS)
if (dots) { mvwaddstr(topwin, 0, 2, BRANDING);
mvwaddnstr(topwin, 0, verlen - 1, prefix, actual_x(prefix, else {
prefixlen)); verlen = 2;
if (space <= -3 || newfie) /* If things don't fit yet, give up the placeholder. */
goto the_end; if (verlen + prefixlen + pathlen + pluglen + statelen > COLS)
waddch(topwin, ' '); pluglen = 0;
waddnstr(topwin, "...", space + 3); /* If things still don't fit, give up the side spaces. */
if (space <= 0) if (verlen + prefixlen + pathlen + pluglen + statelen > COLS) {
goto the_end; verlen = 0;
waddstr(topwin, exppath); statelen -= 2;
} else {
size_t exppathlen = newfie ? 0 : strlenpt(exppath);
/* The length of the expanded filename. */
/* There is room for the whole filename, so we center it. */
mvwaddnstr(topwin, 0, verlen + ((space - exppathlen) / 3),
prefix, actual_x(prefix, prefixlen));
if (!newfie) {
waddch(topwin, ' ');
waddstr(topwin, exppath);
} }
} }
the_end: /* If we have side spaces left, center the path name. */
free(exppath); if (verlen > 0)
offset = verlen + (COLS - (verlen + pluglen + statelen) -
if (state[0] != '\0') { (prefixlen + pathlen)) / 2;
if (statelen >= COLS - 1)
mvwaddnstr(topwin, 0, 0, state, actual_x(state, COLS));
else {
assert(COLS - statelen - 1 >= 0);
mvwaddnstr(topwin, 0, COLS - statelen - 1, state, /* Only print the prefix when there is room for it. */
actual_x(state, statelen)); if (verlen + prefixlen + pathlen + pluglen + statelen <= COLS) {
} mvwaddstr(topwin, 0, offset, prefix);
if (prefixlen > 0)
waddstr(topwin, " ");
} else
wmove(topwin, 0, offset);
/* Print the full path if there's room; otherwise, dottify it. */
if (pathlen + pluglen + statelen <= COLS)
waddstr(topwin, path);
else if (5 + statelen <= COLS) {
waddstr(topwin, "...");
fragment = display_string(path, 3 + pathlen - COLS + statelen,
COLS - statelen, FALSE);
waddstr(topwin, fragment);
free(fragment);
} }
/* Right-align the state if there's room; otherwise, trim it. */
if (statelen > 0 && statelen <= COLS)
mvwaddstr(topwin, 0, COLS - statelen, state);
else if (statelen > 0)
mvwaddnstr(topwin, 0, 0, state, actual_x(state, COLS));
wattroff(topwin, A_BOLD); wattroff(topwin, A_BOLD);
wattroff(topwin, interface_color_pair[TITLE_BAR].pairnum); wattroff(topwin, interface_color_pair[TITLE_BAR].pairnum);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment