Make sure text fits tightly terminal + simplified logic

This commit is contained in:
Jari Vetoniemi 2014-04-14 19:00:03 +03:00
parent f410a5e391
commit 066c5c2e61

View File

@ -87,12 +87,12 @@ static struct curses {
int oldStdout; int oldStdout;
} curses; } curses;
static int _bmDrawCursesResizeBuffer(char **buffer, size_t osize, size_t nsize) static int _bmDrawCursesResizeBuffer(char **buffer, size_t *osize, size_t nsize)
{ {
assert(buffer); assert(buffer);
assert(nsize); assert(osize);
if (nsize == 0 || nsize < osize) if (nsize == 0 || nsize <= *osize)
return 0; return 0;
void *tmp; void *tmp;
@ -101,14 +101,13 @@ static int _bmDrawCursesResizeBuffer(char **buffer, size_t osize, size_t nsize)
return 0; return 0;
if (*buffer) { if (*buffer) {
memcpy(tmp, *buffer, osize); memcpy(tmp, *buffer, *osize);
free(*buffer); free(*buffer);
} }
} }
*buffer = tmp; *buffer = tmp;
memset(*buffer + osize, ' ', (nsize - osize)); *osize = nsize;
(*buffer)[nsize - 1] = 0;
return 1; return 1;
} }
@ -117,32 +116,27 @@ __attribute__((format(printf, 3, 4)))
#endif #endif
static void _bmDrawCursesDrawLine(int pair, int y, const char *format, ...) static void _bmDrawCursesDrawLine(int pair, int y, const char *format, ...)
{ {
static int blen = 0; static size_t blen = 0;
static char *buffer = NULL; static char *buffer = NULL;
int ncols = curses.getmaxx(curses.stdscr); size_t ncols = curses.getmaxx(curses.stdscr);
if (ncols <= 0) if (ncols <= 0)
return; return;
va_list args; va_list args;
va_start(args, format); va_start(args, format);
int nlen = vsnprintf(NULL, 0, format, args) + 1; size_t nlen = vsnprintf(NULL, 0, format, args);
if (nlen < ncols)
nlen = ncols;
va_end(args); va_end(args);
if ((!buffer || nlen > blen) && !_bmDrawCursesResizeBuffer(&buffer, blen, nlen)) if ((!buffer || nlen > blen) && !_bmDrawCursesResizeBuffer(&buffer, &blen, nlen + 1))
return; return;
blen = nlen;
va_start(args, format); va_start(args, format);
int slen = vsnprintf(buffer, blen - 1, format, args); vsnprintf(buffer, blen - 1, format, args);
memset(buffer + slen, ' ', (blen - slen));
buffer[blen - 1] = 0;
va_end(args); va_end(args);
int dw = 0, i = 0; size_t dw = 0, i = 0;
while (dw < ncols && i < blen) { while (dw < ncols && i < nlen) {
if (buffer[i] == '\t') buffer[i] = ' '; if (buffer[i] == '\t') buffer[i] = ' ';
int next = _bmUtf8RuneNext(buffer, i); int next = _bmUtf8RuneNext(buffer, i);
dw += _bmUtf8RuneWidth(buffer + i, next); dw += _bmUtf8RuneWidth(buffer + i, next);
@ -150,12 +144,27 @@ static void _bmDrawCursesDrawLine(int pair, int y, const char *format, ...)
} }
if (dw < ncols) { if (dw < ncols) {
if (!_bmDrawCursesResizeBuffer(&buffer, blen - 1, blen + (ncols - dw))) /* line is too short, widen it */
return; size_t offset = i + (ncols - dw);
if (blen <= offset && !_bmDrawCursesResizeBuffer(&buffer, &blen, offset + 1))
return;
memset(buffer + nlen, ' ', offset - nlen);
buffer[offset] = 0;
} else if (i < blen) { } else if (i < blen) {
int cc = dw - (dw - ncols); /* line is too long, shorten it */
i -= _bmUtf8RunePrev(buffer, i - (dw - ncols)) - 1;
size_t cc = dw - (dw - ncols);
size_t offset = i - (dw - ncols) + (ncols - cc) + 1;
if (blen <= offset) {
int diff = offset - blen + 1;
if (!_bmDrawCursesResizeBuffer(&buffer, &blen, blen + diff))
return;
}
memset(buffer + i - (dw - ncols), ' ', (ncols - cc) + 1); memset(buffer + i - (dw - ncols), ' ', (ncols - cc) + 1);
buffer[i - (dw - ncols) + (ncols - cc) + 1] = 0; buffer[offset] = 0;
} }
if (pair > 0) if (pair > 0)