From b12e5ad7cd57b91a148fcb96cad471ae8f5c22c2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Kapu=C5=9Bci=C5=84ski?= Date: Wed, 9 Aug 2023 21:43:15 +0200 Subject: [PATCH] Replaced boost::replace_all with StrUtils::Replace Also fixed a bug in it and added tests for it. Changes based on https://github.com/osiox/colobot/commit/f0f6f61cabbc9269c83d74974bb24c2933b4bde4 --- CBot/src/CBot/CBotDebug.cpp | 22 +++++++--- src/common/stringutils.cpp | 2 +- src/level/parser/parser.cpp | 12 +++--- src/ui/controls/edit.cpp | 4 +- test/unit/CMakeLists.txt | 1 + test/unit/common/stringutils_test.cpp | 60 +++++++++++++++++++++++++++ 6 files changed, 87 insertions(+), 14 deletions(-) create mode 100644 test/unit/common/stringutils_test.cpp diff --git a/CBot/src/CBot/CBotDebug.cpp b/CBot/src/CBot/CBotDebug.cpp index fa21acaf..1f39fd83 100644 --- a/CBot/src/CBot/CBotDebug.cpp +++ b/CBot/src/CBot/CBotDebug.cpp @@ -63,13 +63,25 @@ void CBotDebug::DumpCompiledProgram(CBotProgram* program) if (finished.find(instr) != finished.end()) return; finished.insert(instr); - std::string label = ""+instr->GetDebugName()+"\n"; + auto replaceAll = [](std::string& text, const std::string& from, const std::string& to) + { + std::size_t pos = 0; + + while ((pos = text.find(from, pos)) != std::string::npos) + { + text.replace(pos, from.length(), to); + pos += to.length(); + } + }; + std::string data = instr->GetDebugData(); - boost::algorithm::replace_all(data, "&", "&"); - boost::algorithm::replace_all(data, "<", "<"); - boost::algorithm::replace_all(data, ">", ">"); + replaceAll(data, "&", "&"); + replaceAll(data, "<", "<"); + replaceAll(data, ">", ">"); + + std::string label = ""+instr->GetDebugName()+"\n"; label += data; - boost::algorithm::replace_all(label, "\n", "
"); + replaceAll(label, "\n", "
"); std::string additional = ""; if (instr->GetDebugName() == "CBotFunction") diff --git a/src/common/stringutils.cpp b/src/common/stringutils.cpp index 8ce69cbb..4c49d3f3 100644 --- a/src/common/stringutils.cpp +++ b/src/common/stringutils.cpp @@ -76,7 +76,7 @@ std::string StrUtils::Replace(const std::string &str, const std::string &oldStr, { std::string result = str; std::size_t pos = 0; - while ((pos = str.find(oldStr, pos)) != std::string::npos) + while ((pos = result.find(oldStr, pos)) != std::string::npos) { result.replace(pos, oldStr.length(), newStr); pos += newStr.length(); diff --git a/src/level/parser/parser.cpp b/src/level/parser/parser.cpp index c79519d5..b90c150d 100644 --- a/src/level/parser/parser.cpp +++ b/src/level/parser/parser.cpp @@ -167,7 +167,7 @@ void CLevelParser::Load() { lineNumber++; - boost::replace_all(line, "\t", " "); // replace tab by space + line = StrUtils::Replace(line, "\t", " "); // replace tab by space // ignore comments size_t pos = 0; @@ -337,9 +337,9 @@ void CLevelParser::SetLevelPaths(LevelCategory category, int chapter, int rank) std::string CLevelParser::InjectLevelPaths(const std::string& path, const std::string& defaultDir) { std::string newPath = path; - if(!m_pathLvl.empty() ) boost::replace_all(newPath, "%lvl%", m_pathLvl); - if(!m_pathChap.empty()) boost::replace_all(newPath, "%chap%", m_pathChap); - if(!m_pathCat.empty() ) boost::replace_all(newPath, "%cat%", m_pathCat); + if(!m_pathLvl.empty() ) newPath = StrUtils::Replace(newPath, "%lvl%", m_pathLvl); + if(!m_pathChap.empty()) newPath = StrUtils::Replace(newPath, "%chap%", m_pathChap); + if(!m_pathCat.empty() ) newPath = StrUtils::Replace(newPath, "%cat%", m_pathCat); if(newPath == path && !path.empty()) { newPath = defaultDir + (!defaultDir.empty() ? "/" : "") + newPath; @@ -347,12 +347,12 @@ std::string CLevelParser::InjectLevelPaths(const std::string& path, const std::s std::string langPath = newPath; std::string langStr(1, CApplication::GetInstancePointer()->GetLanguageChar()); - boost::replace_all(langPath, "%lng%", langStr); + langPath = StrUtils::Replace(langPath, "%lng%", langStr); if(CResourceManager::Exists(langPath)) return langPath; // Fallback to English if file doesn't exist - boost::replace_all(newPath, "%lng%", "E"); + newPath = StrUtils::Replace(newPath, "%lng%", "E"); if(CResourceManager::Exists(newPath)) return newPath; diff --git a/src/ui/controls/edit.cpp b/src/ui/controls/edit.cpp index f52f392b..d0cb235f 100644 --- a/src/ui/controls/edit.cpp +++ b/src/ui/controls/edit.cpp @@ -820,7 +820,7 @@ void CEdit::HyperJump(std::string name, std::string marker) std::string filename = name + std::string(".txt"); filename = InjectLevelPathsForCurrentLevel(filename, "help/%lng%"); - boost::replace_all(filename, "\\", "/"); //TODO: Fix this in files + filename = StrUtils::Replace(filename, "\\", "/"); //TODO: Fix this in files if ( ReadText(filename) ) { @@ -1172,7 +1172,7 @@ static std::string PrepareImageFilename(std::string name) std::string filename; filename = name + ".png"; filename = InjectLevelPathsForCurrentLevel(filename, "icons"); - boost::replace_all(filename, "\\", "/"); // TODO: Fix this in files + filename = StrUtils::Replace(filename, "\\", "/"); // TODO: Fix this in files return filename; } diff --git a/test/unit/CMakeLists.txt b/test/unit/CMakeLists.txt index 99affae8..8b7792c2 100644 --- a/test/unit/CMakeLists.txt +++ b/test/unit/CMakeLists.txt @@ -15,6 +15,7 @@ add_executable(colobot_ut CBot/CBotFileUtils_test.cpp CBot/CBotToken_test.cpp common/config_file_test.cpp + common/stringutils_test.cpp common/timeutils_test.cpp #graphics/engine/lightman_test.cpp math/func_test.cpp diff --git a/test/unit/common/stringutils_test.cpp b/test/unit/common/stringutils_test.cpp new file mode 100644 index 00000000..9411bdb9 --- /dev/null +++ b/test/unit/common/stringutils_test.cpp @@ -0,0 +1,60 @@ +/* + * This file is part of the Colobot: Gold Edition source code + * Copyright (C) 2001-2023, Daniel Roux, EPSITEC SA & TerranovaTeam + * http://epsitec.ch; http://colobot.info; http://github.com/colobot + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + * See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see http://gnu.org/licenses + */ + +#include "common/stringutils.h" + +#include + +namespace StringUtilsTesta +{ + +TEST(StringUtilTests, ReplaceShortToLong) +{ + std::string text = "Test {123}, {123}, {123}{123} Test"; + + auto result = StrUtils::Replace(text, "{123}", "[0987654]"); + + std::string expected = "Test [0987654], [0987654], [0987654][0987654] Test"; + + EXPECT_TRUE(result == expected); +} + +TEST(StringUtilTests, ReplaceLongToShort) +{ + std::string text = "Test {1234567}, {1234567}, {1234567}{1234567} Test"; + + auto result = StrUtils::Replace(text, "{1234567}", "[64]"); + + std::string expected = "Test [64], [64], [64][64] Test"; + + EXPECT_TRUE(result == expected); +} + +TEST(StringUtilTests, ReplaceSameLength) +{ + std::string text = "Test {123}, {123}, {123}{123} Test"; + + auto result = StrUtils::Replace(text, "{123}", "[432]"); + + std::string expected = "Test [432], [432], [432][432] Test"; + + EXPECT_TRUE(result == expected); +} + +} // namespace StringUtils