diff options
author | Max Horn | 2003-06-08 00:39:08 +0000 |
---|---|---|
committer | Max Horn | 2003-06-08 00:39:08 +0000 |
commit | faadbcafa70365bf3ee1b48efff5b94d62fcece2 (patch) | |
tree | 5d248ffca0c9c224ac2c3f5476171c29d7388f19 /scumm/smush | |
parent | f273c4195b77ce699520071cdec410fcfa54bdb8 (diff) | |
download | scummvm-rg350-faadbcafa70365bf3ee1b48efff5b94d62fcece2.tar.gz scummvm-rg350-faadbcafa70365bf3ee1b48efff5b94d62fcece2.tar.bz2 scummvm-rg350-faadbcafa70365bf3ee1b48efff5b94d62fcece2.zip |
cleanup; got rid of the split function and rather work in place (so instead of allocating dozens of small goblets of memory, we only need to duplicate the string once); fixed some text positioning bugs (but again, to get a real accurate implementation, I'll need to study screen shots of the Dig/FT/COMI videos and compare them to our results)
svn-id: r8388
Diffstat (limited to 'scumm/smush')
-rw-r--r-- | scumm/smush/smush_font.cpp | 237 | ||||
-rw-r--r-- | scumm/smush/smush_font.h | 8 | ||||
-rw-r--r-- | scumm/smush/smush_player.cpp | 8 |
3 files changed, 99 insertions, 154 deletions
diff --git a/scumm/smush/smush_font.cpp b/scumm/smush/smush_font.cpp index 841d4270bc..38d6ffaa6b 100644 --- a/scumm/smush/smush_font.cpp +++ b/scumm/smush/smush_font.cpp @@ -33,6 +33,7 @@ SmushFont::SmushFont(bool use_original_colors, bool new_colors) : } int SmushFont::getStringWidth(const char *str) { + assert(str); if (!_loaded) { warning("SmushFont::getStringWidth() Font is not loaded"); return 0; @@ -46,6 +47,7 @@ int SmushFont::getStringWidth(const char *str) { } int SmushFont::getStringHeight(const char *str) { + assert(str); if (!_loaded) { warning("SmushFont::getStringHeight() Font is not loaded"); return 0; @@ -134,30 +136,6 @@ int SmushFont::draw2byte(byte *buffer, int dst_width, int x, int y, int idx) { return w + 1; } -static char **split(const char *str, char sep) { - char **ret = new char *[62]; - int n = 0; - const char *i = str; - char *j = strchr(i, sep); - - while (j != NULL) { - assert(n < 60); - ret[n] = new char[j - i + 1]; - memcpy(ret[n], i, j - i); - ret[n++][j - i] = 0; - i = j + 1; - j = strchr(i, sep); - } - - int len = strlen(i); - ret[n] = new char[len + 1]; - memcpy(ret[n], i, len); - ret[n++][len] = 0; - ret[n] = 0; - - return ret; -} - void SmushFont::drawSubstring(const char *str, byte *buffer, int dst_width, int x, int y) { for (int i = 0; str[i] != 0; i++) { if ((byte)str[i] >= 0x80 && _vm->_CJKMode) { @@ -168,6 +146,9 @@ void SmushFont::drawSubstring(const char *str, byte *buffer, int dst_width, int } } +#define MAX_WORDS 60 + + void SmushFont::drawStringAbsolute(const char *str, byte *buffer, int dst_width, int x, int y) { debug(9, "SmushFont::drawStringAbsolute(%s, %d, %d)", str, x, y); @@ -187,138 +168,116 @@ void SmushFont::drawStringAbsolute(const char *str, byte *buffer, int dst_width, } } -void SmushFont::drawStringCentered(const char *str, byte *buffer, int dst_width, int dst_height, int y, int xmin, int width, int offset) { - debug(9, "SmushFont::drawStringCentered(%s, %d, %d)", str, xmin, y); +void SmushFont::drawStringCentered(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right) { + debug(9, "SmushFont::drawStringCentered(%s, %d, %d, %d, %d)", str, x, y, left, right); - char *z = strchr(str, '\n'); - if (z != 0) { - // FIXME: this is actually evil, because it silently modifes the - // string 'str' passed to us, despite it being declared const. - warning("drawStringCentered: got input string containing \\n"); - *z = 0; - } - char **words = split(str, ' '); + const int width = right - left; + char *s = strdup(str); + char *words[MAX_WORDS]; int word_count = 0; - while (words[word_count]) - word_count++; + char *tmp = s; + while (tmp) { + assert(word_count < MAX_WORDS); + words[word_count++] = tmp; + tmp = strpbrk(tmp, " \t\r\n"); + if (tmp == 0) + break; + *tmp++ = 0; + } int i = 0, max_width = 0, height = 0, line_count = 0; - char **substrings = new char *[word_count]; - int *substr_widths = new int[word_count]; - int space_width = getCharWidth(' '); + char *substrings[MAX_WORDS]; + int substr_widths[MAX_WORDS]; + const int space_width = getCharWidth(' '); i = 0; while (i < word_count) { - int substr_width = getStringWidth(words[i]); - char *substr = new char[1000]; - strcpy(substr, words[i]); - int j = i + 1; + char *substr = words[i++]; + int substr_width = getStringWidth(substr); - while (j < word_count) { - int word_width = getStringWidth(words[j]); + while (i < word_count) { + int word_width = getStringWidth(words[i]); if ((substr_width + space_width + word_width) >= width) break; substr_width += word_width + space_width; - j++; - } - - for (int k = i + 1; k < j; k++) { - strcat(substr, " "); - strcat(substr, words[k]); + *(words[i]-1) = ' '; // Convert 0 byte back to space + i++; } substrings[line_count] = substr; substr_widths[line_count++] = substr_width; - if (substr_width > max_width) + if (max_width < substr_width) max_width = substr_width; - i = j; height += getStringHeight(substr); } - for (i = 0; i < word_count; i++) { - delete[] words[i]; - } - delete[] words; - if (y > dst_height - height) { y = dst_height - height; } max_width = (max_width + 1) >> 1; - int x = xmin + width / 2 + offset - dst_width / 2; + x = left + width / 2; - if (x < max_width) - x = max_width; - if (x > dst_width - max_width) - x = dst_width - max_width; + if (x < left + max_width) + x = left + max_width; + if (x > right - max_width) + x = right - max_width; for (i = 0; i < line_count; i++) { drawSubstring(substrings[i], buffer, dst_width, x - substr_widths[i] / 2, y); y += getStringHeight(substrings[i]); - delete[] substrings[i]; } - - delete[] substr_widths; - delete[] substrings; + + free(s); } -void SmushFont::drawStringWrap(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int width) { - debug(9, "SmushFont::drawStringWrap(%s, %d, %d)", str, x, y); +void SmushFont::drawStringWrap(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right) { + debug(9, "SmushFont::drawStringWrap(%s, %d, %d, %d, %d)", str, x, y, left, right); - char *z = strchr(str, '\n'); - if (z != 0) { - // FIXME: this is actually evil, because it silently modifes the - // string 'str' passed to us, despite it being declared const. - warning("drawStringWrap: got input string containing \\n"); - *z = 0; - } - char **words = split(str, ' '); + const int width = right - left; + char *s = strdup(str); + char *words[MAX_WORDS]; int word_count = 0; - while (words[word_count]) - word_count++; + char *tmp = s; + while (tmp) { + assert(word_count < MAX_WORDS); + words[word_count++] = tmp; + tmp = strpbrk(tmp, " \t\r\n"); + if (tmp == 0) + break; + *tmp++ = 0; + } int i = 0, max_width = 0, height = 0, line_count = 0; - char **substrings = new char *[word_count]; - int *substr_widths = new int[word_count]; - int space_width = getCharWidth(' '); + char *substrings[MAX_WORDS]; + int substr_widths[MAX_WORDS]; + const int space_width = getCharWidth(' '); i = 0; while (i < word_count) { - int substr_width = getStringWidth(words[i]); - char *substr = new char[1000]; - strcpy(substr, words[i]); - int j = i + 1; + char *substr = words[i++]; + int substr_width = getStringWidth(substr); - while (j < word_count) { - int word_width = getStringWidth(words[j]); + while (i < word_count) { + int word_width = getStringWidth(words[i]); if ((substr_width + space_width + word_width) >= width) break; substr_width += word_width + space_width; - j++; - } - - for (int k = i + 1; k < j; k++) { - strcat(substr, " "); - strcat(substr, words[k]); + *(words[i]-1) = ' '; // Convert 0 byte back to space + i++; } substrings[line_count] = substr; substr_widths[line_count++] = substr_width; if (max_width < substr_width) max_width = substr_width; - i = j; height += getStringHeight(substr); } - for (i = 0; i < word_count; i++) { - delete[] words[i]; - } - delete[] words; - if (y > dst_height - height) { y = dst_height - height; } @@ -329,86 +288,72 @@ void SmushFont::drawStringWrap(const char *str, byte *buffer, int dst_width, int for (i = 0; i < line_count; i++) { drawSubstring(substrings[i], buffer, dst_width, x, y); y += getStringHeight(substrings[i]); - delete[] substrings[i]; } - - delete[] substr_widths; - delete[] substrings; + + free(s); } -void SmushFont::drawStringWrapCentered(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int width) { - debug(9, "SmushFont::drawStringWrapCentered(%s, %d, %d)", str, x, y); +void SmushFont::drawStringWrapCentered(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right) { + debug(9, "SmushFont::drawStringWrapCentered(%s, %d, %d, %d, %d)", str, x, y, left, right); - char *z = strchr(str, '\n'); - if (z != 0) { - // FIXME: this is actually evil, because it silently modifes the - // string 'str' passed to us, despite it being declared const. - warning("drawStringWrapCentered: got input string containing \\n"); - *z = 0; - } - char **words = split(str, ' '); + const int width = right - left; + char *s = strdup(str); + char *words[MAX_WORDS]; int word_count = 0; - while (words[word_count]) - word_count++; + char *tmp = s; + while (tmp) { + assert(word_count < MAX_WORDS); + words[word_count++] = tmp; + tmp = strpbrk(tmp, " \t\r\n"); + if (tmp == 0) + break; + *tmp++ = 0; + } int i = 0, max_width = 0, height = 0, line_count = 0; - char **substrings = new char *[word_count]; - int *substr_widths = new int[word_count]; - int space_width = getCharWidth(' '); + char *substrings[MAX_WORDS]; + int substr_widths[MAX_WORDS]; + const int space_width = getCharWidth(' '); i = 0; - width = MIN(width, dst_width); while (i < word_count) { - int substr_width = getStringWidth(words[i]); - char *substr = new char[1000]; - strcpy(substr, words[i]); - int j = i + 1; + char *substr = words[i++]; + int substr_width = getStringWidth(substr); - while (j < word_count) { - int word_width = getStringWidth(words[j]); + while (i < word_count) { + int word_width = getStringWidth(words[i]); if ((substr_width + space_width + word_width) >= width) break; substr_width += word_width + space_width; - j++; - } - - for (int k = i + 1; k < j; k++) { - strcat(substr, " "); - strcat(substr, words[k]); + *(words[i]-1) = ' '; // Convert 0 byte back to space + i++; } substrings[line_count] = substr; substr_widths[line_count++] = substr_width; if (max_width < substr_width) max_width = substr_width; - i = j; height += getStringHeight(substr); } - for (i = 0; i < word_count; i++) { - delete[] words[i]; - } - delete[] words; - if (y > dst_height - height) { y = dst_height - height; } max_width = (max_width + 1) >> 1; + x = left + width / 2; - if (x < max_width) - x = max_width; - if (x > dst_width - max_width) - x = dst_width - max_width; + if (x < left + max_width) + x = left + max_width; + if (x > right - max_width) + x = right - max_width; for (i = 0; i < line_count; i++) { drawSubstring(substrings[i], buffer, dst_width, x - substr_widths[i] / 2, y); y += getStringHeight(substrings[i]); - delete[] substrings[i]; } - - delete[] substr_widths; - delete[] substrings; + + free(s); } diff --git a/scumm/smush/smush_font.h b/scumm/smush/smush_font.h index 540df96662..ae5932693a 100644 --- a/scumm/smush/smush_font.h +++ b/scumm/smush/smush_font.h @@ -43,10 +43,10 @@ public: SmushFont(bool use_original_colors, bool new_colors); void setColor(byte c) { _color = c; } - void drawStringCentered(const char *str, byte *buffer, int dst_width, int dst_height, int y, int xmin, int width, int offset); - void drawStringWrap(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int width); - void drawStringWrapCentered(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int width); - void drawStringAbsolute(const char *str, byte *buffer, int dst_width, int x, int y); + void drawStringAbsolute (const char *str, byte *buffer, int dst_width, int x, int y); + void drawStringCentered (const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right); + void drawStringWrap (const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right); + void drawStringWrapCentered(const char *str, byte *buffer, int dst_width, int dst_height, int x, int y, int left, int right); }; #endif diff --git a/scumm/smush/smush_player.cpp b/scumm/smush/smush_player.cpp index 311d375431..92fce74919 100644 --- a/scumm/smush/smush_player.cpp +++ b/scumm/smush/smush_player.cpp @@ -484,7 +484,7 @@ void SmushPlayer::handleTextResource(Chunk &b) { int flags = b.getShort(); int left = b.getShort(); int top = b.getShort(); - int width = b.getShort(); + int right = b.getShort(); /*int32 height =*/ b.getShort(); /*int32 unk2 =*/ b.getWord(); @@ -561,13 +561,13 @@ void SmushPlayer::handleTextResource(Chunk &b) { sf->drawStringAbsolute(str, _data, _width, pos_x, pos_y); break; case 1: - sf->drawStringCentered(str, _data, _width, _height, MAX(pos_y, top), left, width, pos_x); + sf->drawStringCentered(str, _data, _width, _height, pos_x, MAX(pos_y, top), left, right); break; case 8: - sf->drawStringWrap(str, _data, _width, _height, pos_x, MAX(pos_y, top), width); + sf->drawStringWrap(str, _data, _width, _height, pos_x, MAX(pos_y, top), left, right); break; case 9: - sf->drawStringWrapCentered(str, _data, _width, _height, pos_x, MAX(pos_y, top), width); + sf->drawStringWrapCentered(str, _data, _width, _height, pos_x, MAX(pos_y, top), left, right); break; default: warning("SmushPlayer::handleTextResource. Not handled flags: %d", flags); |