From dda0f77bcf093dced1ad833982be8a9e0951a85e Mon Sep 17 00:00:00 2001 From: Colin Snover Date: Sat, 7 Oct 2017 22:01:13 -0500 Subject: COMMON: Add basic fixed-width word wrap to Common::String --- common/str.cpp | 38 ++++++++++++++++++++++++++++++++++++++ common/str.h | 11 +++++++++++ test/common/str.h | 22 ++++++++++++++++++++++ 3 files changed, 71 insertions(+) diff --git a/common/str.cpp b/common/str.cpp index 3a0fd6a08e..2ef67175cd 100644 --- a/common/str.cpp +++ b/common/str.cpp @@ -444,6 +444,44 @@ void String::trim() { } } +void String::wordWrap(const uint32 maxLength) { + if (_size < maxLength) { + return; + } + + makeUnique(); + + enum { kNoSpace = 0xFFFFFFFF }; + + uint32 i = 0; + while (i < _size) { + uint32 lastSpace = kNoSpace; + uint32 x = 0; + while (i < _size && x <= maxLength) { + const char c = _str[i]; + if (c == '\n') { + lastSpace = kNoSpace; + x = 0; + } else { + if (Common::isSpace(c)) { + lastSpace = i; + } + ++x; + } + ++i; + } + + if (x > maxLength) { + if (lastSpace == kNoSpace) { + insertChar('\n', i - 1); + } else { + setChar('\n', lastSpace); + i = lastSpace + 1; + } + } + } +} + uint String::hash() const { return hashit(c_str()); } diff --git a/common/str.h b/common/str.h index ba1e0b8341..fd77fa90c8 100644 --- a/common/str.h +++ b/common/str.h @@ -235,6 +235,17 @@ public: */ void trim(); + /** + * Wraps the text in the string to the given line maximum. Lines will be + * broken at any whitespace character. New lines are assumed to be + * represented using '\n'. + * + * This is a very basic line wrap which does not perform tab stop + * calculation, consecutive whitespace collapsing, auto-hyphenation, or line + * balancing. + */ + void wordWrap(const uint32 maxLength); + uint hash() const; /**@{ diff --git a/test/common/str.h b/test/common/str.h index b7ad28e56e..9f8c6fbd60 100644 --- a/test/common/str.h +++ b/test/common/str.h @@ -443,6 +443,28 @@ class StringTestSuite : public CxxTest::TestSuite TS_ASSERT_LESS_THAN(scumm_strnicmp("abCd", "ABCde", 5), 0); } + void test_wordWrap() { + Common::String testString("123456"); + testString.wordWrap(10); + TS_ASSERT(testString == "123456"); + testString.wordWrap(2); + TS_ASSERT(testString == "12\n34\n56"); + testString = "1234 5678"; + testString.wordWrap(4); + TS_ASSERT(testString == "1234\n5678"); + testString = "12 3 45"; + testString.wordWrap(4); + TS_ASSERT(testString == "12 3\n45"); + testString = "\n1\n23 45\n\n"; + testString.wordWrap(3); + TS_ASSERT(testString == "\n1\n23\n45\n\n"); + testString = "123 "; + testString.wordWrap(4); + TS_ASSERT(testString == "123 "); + testString.wordWrap(3); + TS_ASSERT(testString == "123\n"); + } + void test_replace() { // Tests created with the results of the STL std::string class -- cgit v1.2.3