Skip to content

Commit

Permalink
Fix display of Unicode text in many views
Browse files Browse the repository at this point in the history
This commit also adds the strwidth function and consolidates the TDrawBuffer interface.
  • Loading branch information
magiblot committed Jul 27, 2020
1 parent 0e0f488 commit 81066ee
Show file tree
Hide file tree
Showing 10 changed files with 117 additions and 97 deletions.
9 changes: 5 additions & 4 deletions include/tvision/drawbuf.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ class TDrawBuffer

void moveChar( ushort indent, char c, ushort attr, ushort count );
void moveStr( ushort indent, const char _FAR *str, ushort attrs );
void moveStr( ushort indent, const char _FAR *str, ushort attr, ushort width, ushort begin=0 );
void moveCStr( ushort indent, const char _FAR *str, ushort attrs );
void moveBuf( ushort indent, const void _FAR *source,
ushort attr, ushort count );
Expand All @@ -52,10 +53,10 @@ class TDrawBuffer

#ifndef __BORLANDC__
// Multibyte compatible operations

void moveStrEx( ushort indent, std::string_view str, ushort attrs );
void moveCStrEx( ushort indent, std::string_view str, ushort attrs );
void moveBufEx( ushort indent, TScreenCell *source, ushort attr, ushort count );
void moveStr( ushort indent, std::string_view str, ushort attrs );
void moveStr( ushort indent, std::string_view str, ushort attr, ushort width, ushort begin=0 );
void moveCStr( ushort indent, std::string_view str, ushort attrs );
void moveBuf( ushort indent, TScreenCell *source, ushort attr, ushort count );
#endif

#ifdef __FLAT__
Expand Down
6 changes: 4 additions & 2 deletions include/tvision/util.h
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,10 @@ const char *historyStr( uchar id, int index );
void historyAdd( uchar id, const char * );

int cstrlen( const char * );
int strwidth( const char * );
#ifndef __BORLANDC__
int cstrlen(std::string_view s);
int cstrlen( std::string_view s );
int strwidth( std::string_view s );
#endif

class _FAR TView;
Expand All @@ -67,7 +69,7 @@ void getCurDir( char *dir );

Boolean isWild( const char *f );

char *strnzcpy( char *dest, const char *src, size_t n ); // misc.cpp
char *strnzcpy( char *dest, const char *src, size_t n );

unsigned int fast_utoa( uint value, char *buffer );

Expand Down
126 changes: 59 additions & 67 deletions source/tvision/drivers.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -113,28 +113,12 @@ I POP DS
*(uchar *)dest++ = *s++;

#else
return moveStrEx(indent, std::string_view {(const char*) source, count}, attr);
#if 0
TScreenCell *dest = &data[indent];
TScreenCell *limit = &data[dataLength];
uchar *s = (uchar *) source;
if (attr)
for (; dest < limit && count; --count, ++s, ++dest)
{
TScreenCell c {};
c.Char = (uchar) *s;
c.Attr = (uchar) attr;
*dest = c;
}
else
while (dest < limit && count--)
*dest++ = TScreenCell::fromPair(*s++);
#endif
return moveStr(indent, std::string_view {(const char*) source, count}, attr);
#endif
}

#ifndef __BORLANDC__
void TDrawBuffer::moveBufEx(ushort indent, TScreenCell *source, ushort attr, ushort count)
void TDrawBuffer::moveBuf(ushort indent, TScreenCell *source, ushort attr, ushort count)
{
TScreenCell *dest = &data[indent];
TScreenCell *limit = &data[dataLength];
Expand Down Expand Up @@ -317,35 +301,12 @@ I POP DS
}
}
#else
return moveCStrEx(indent, str, attrs);
#if 0
TScreenCell *dest = &data[indent];
TScreenCell *limit = &data[dataLength];
uchar c;
int toggle = 1;
uchar curAttr = ((uchar *)&attrs)[0];

for (; dest < limit && (c = *str); ++str)
{
if (c == '~')
{
curAttr = ((uchar *) &attrs)[toggle];
toggle = 1 - toggle;
}
else
{
TScreenCell cell {};
cell.Char = (uchar) c;
cell.Attr = (uchar) curAttr;
*dest++ = cell;
}
}
#endif
return moveCStr(indent, std::string_view {str}, attrs);
#endif
}

#ifndef __BORLANDC__
void TDrawBuffer::moveCStrEx( ushort indent, std::string_view str, ushort attrs )
void TDrawBuffer::moveCStr( ushort indent, std::string_view str, ushort attrs )
{
size_t i = indent, j = 0;
int toggle = 1;
Expand Down Expand Up @@ -434,34 +395,12 @@ I POP DS
while (dest < limit && *str)
*(uchar *)dest++ = *str++;
#else
return moveStrEx(indent, str, attr);
#if 0
TScreenCell *dest = &data[indent];
TScreenCell *limit = &data[dataLength];
uchar c;

if (attr)
for (; dest < limit && (c = *str); ++str, ++dest)
{
TScreenCell cell {};
cell.Char = (uchar) c;
cell.Attr = (uchar) attr;
*dest = cell;
}
else
while (dest < limit && *str)
{
auto cell = dest->Cell;
cell.Char = (uchar) *str++;
cell.extraWidth = 0;
*dest++ = cell;;
}
#endif
return moveStr(indent, std::string_view {str}, attr);
#endif
}

#ifndef __BORLANDC__
void TDrawBuffer::moveStrEx( ushort indent, std::string_view str, ushort attr )
void TDrawBuffer::moveStr( ushort indent, std::string_view str, ushort attr )
{
size_t i = indent, j = 0;

Expand All @@ -477,6 +416,59 @@ void TDrawBuffer::moveStrEx( ushort indent, std::string_view str, ushort attr )
}
#endif

/*------------------------------------------------------------------------*/
/* */
/* TDrawBuffer::moveStr (2) */
/* */
/* arguments: */
/* */
/* indent - character position within the buffer where the data */
/* is to go */
/* */
/* str - pointer to a 0-terminated string of characters to */
/* be moved into the buffer */
/* */
/* attr - text attribute to be put into the buffer with each */
/* character in the string. */
/* */
/* width - number of display columns to be copied from str. */
/* */
/* begin - initial display column in str where to start counting. */
/* */
/*------------------------------------------------------------------------*/

void TDrawBuffer::moveStr( ushort indent, const char _FAR *str, ushort attr, ushort width, ushort begin )
{
#ifdef __BORLANDC__
int len = 0;
while (str[len] && len < int(begin + width))
++len;
len -= begin;
if (len > 0)
moveBuf(indent, str + begin, attr, min(width, len));
#else
moveStr(indent, std::string {str}, attr, width, begin);
#endif
}

#ifndef __BORLANDC__
void TDrawBuffer::moveStr( ushort indent, std::string_view str, ushort attr, ushort width, ushort begin )
{
size_t s = 0, remainder = 0;
utf8wseek(str, s, remainder, begin);
if (remainder)
moveChar(indent, ' ', attr, remainder);
size_t d = indent + remainder;
size_t limit = std::min(dataLength, d + width);
while (d < limit && s < str.size())
{
if (attr)
data[d].Attr = (uchar) attr;
utf8read(&data[d], dataLength - d, d, {&str[s], str.size() - s}, s);
}
}
#endif

#ifdef __FLAT__
TDrawBuffer::TDrawBuffer() {
// This makes it possible to create TDrawBuffers for big screen widths.
Expand Down
40 changes: 37 additions & 3 deletions source/tvision/drivers2.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -74,16 +74,16 @@ const ushort arrowCodes[] =

int cstrlen( const char *s )
{
#ifndef __BORLANDC__
return cstrlen(std::string_view {s});
#else
#ifdef __BORLANDC__
int len = 0;
while( *s != EOS )
{
if( *s++ != '~' )
len++;
}
return len;
#else
return cstrlen(std::string_view {s});
#endif
}

Expand All @@ -101,3 +101,37 @@ int cstrlen( std::string_view s )
return width;
}
#endif

/*------------------------------------------------------------------------*/
/* */
/* strwidth */
/* */
/* argument: */
/* */
/* s - pointer to 0-terminated string */
/* */
/* returns */
/* */
/* displayed length of string. */
/* */
/*------------------------------------------------------------------------*/

int strwidth( const char *s )
{
#ifdef __BORLANDC__
return strlen(s);
#else
return strwidth(std::string_view {s});
#endif
}

#ifndef __BORLANDC__
int strwidth( std::string_view s )
{
std::mbstate_t state = {};
size_t i = 0, width = 0;
while (i < s.size())
utf8next(s.substr(i, s.size() - i), i, width, state);
return width;
}
#endif
12 changes: 4 additions & 8 deletions source/tvision/help.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -94,8 +94,6 @@ void THelpViewer::draw()
TDrawBuffer b;
size_t bufLength = b.length();
char *line = (char*) alloca(bufLength);
char *buffer = (char*) alloca(bufLength);
char *bufPtr;
int i, j, l;
int keyCount;
ushort normal, keyword, selKeyword, c;
Expand All @@ -122,13 +120,11 @@ void THelpViewer::draw()
for (i = 1; i <= size.y; ++i)
{
b.moveChar(0, ' ', normal, size.x);
strcpy(line, topic->getLine(i + delta.y, buffer, bufLength));
if (strlen(line) > delta.x)
memset(line, 0, bufLength);
topic->getLine(i + delta.y, line, bufLength-1);
if (strwidth(line) > delta.x)
{
bufPtr = line + delta.x;
strncpy(buffer, bufPtr, size.x);
buffer[size.x] = 0;
b.moveStr(0, buffer, normal);
b.moveStr(0, line, normal, size.x, delta.x);
}
else
b.moveStr(0, "", normal);
Expand Down
2 changes: 1 addition & 1 deletion source/tvision/tframe.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ void TFrame::draw()
l = max( l, 0 );
i = (width - l) >> 1;
b.putChar( i-1, ' ' );
b.moveBuf( i, title, cTitle, l );
b.moveStr( i, title, cTitle, l );
b.putChar( i+l, ' ' );
}
}
Expand Down
2 changes: 1 addition & 1 deletion source/tvision/thstview.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ int THistoryViewer::historyWidth()
int count = historyCount( historyId );
for( int i = 0; i < count; i++ )
{
int T = strlen( historyStr( historyId, i ) );
int T = strwidth( historyStr( historyId, i ) );
width = max( width, T );
}
return width;
Expand Down
9 changes: 2 additions & 7 deletions source/tvision/tinputli.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ Boolean TInputLine::canScroll( int delta )
return Boolean( firstPos > 0 );
else
if( delta > 0 )
return Boolean( strlen(data) - firstPos + 2 > size.x );
return Boolean( strwidth(data) - firstPos + 2 > size.x );
else
return False;
}
Expand All @@ -103,10 +103,7 @@ void TInputLine::draw()
b.moveChar( 0, ' ', color, size.x );
if( size.x > 1 )
{
char buf[256];
strncpy( buf, data+firstPos, size.x - 2 );
buf[size.x - 2 ] = EOS;
b.moveStr( 1, buf, color );
b.moveStr( 1, data, color, size.x - 1, firstPos);
}
if( canScroll(1) )
b.moveChar( size.x-1, rightArrow, getColor(4), 1 );
Expand Down Expand Up @@ -317,8 +314,6 @@ void TInputLine::handleEvent( TEvent& event )
{
strcpy( data+curPos-1, data+curPos );
curPos--;
if( firstPos > 0 )
firstPos--;
checkValid(True);
}
break;
Expand Down
4 changes: 2 additions & 2 deletions source/tvision/tlstview.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -131,8 +131,8 @@ void TListViewer::draw()
if (indent < 255)
{
char text[256] = {0};
getText( text, item, min(colWidth + indent, 255) );
b.moveStr( curCol+1, text + indent, color );
getText( text, item, 255 );
b.moveStr( curCol+1, text, color, colWidth, indent );
}
if( showMarkers )
{
Expand Down
4 changes: 2 additions & 2 deletions source/tvision/tmenubox.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ static TRect getRect( const TRect& bounds, TMenu *aMenu )
l += 3;
else
if( p->param != 0 )
l += cstrlen(p->param) + 2;
l += strwidth(p->param) + 2;
w = max( l, w );
}
h++;
Expand Down Expand Up @@ -110,7 +110,7 @@ void TMenuBox::draw()
if( p->command == 0 )
b.putChar( size.x-4, 16 );
else if( p->param != 0 )
b.moveStr( size.x-3-strlen(p->param),
b.moveStr( size.x-3-strwidth(p->param),
p->param,
color);
}
Expand Down

0 comments on commit 81066ee

Please sign in to comment.