diff --git a/radio/src/gui/colorlcd/mainview/screen_setup.cpp b/radio/src/gui/colorlcd/mainview/screen_setup.cpp index 380bc5949..ce40cef33 100644 --- a/radio/src/gui/colorlcd/mainview/screen_setup.cpp +++ b/radio/src/gui/colorlcd/mainview/screen_setup.cpp @@ -317,7 +317,8 @@ ScreenAddPage::ScreenAddPage(const PageDef& pageDef) : PageGroupItem(pageDef) void ScreenAddPage::build(Window* window) { - std::string s = replaceAll(STR_QM_ADD_SCREEN, "\n", " "); + std::string s(STR_QM_ADD_SCREEN); + strReplaceAll(s, "\n", " "); new TextButton(window, rect_t{LCD_W / 2 - ADD_TXT_W / 2, window->height() / 2 - EdgeTxStyles::UI_ELEMENT_HEIGHT, ADD_TXT_W, EdgeTxStyles::UI_ELEMENT_HEIGHT}, diff --git a/radio/src/gui/colorlcd/setup_menus/pagegroup.cpp b/radio/src/gui/colorlcd/setup_menus/pagegroup.cpp index 6f2458c77..b4084c2b4 100644 --- a/radio/src/gui/colorlcd/setup_menus/pagegroup.cpp +++ b/radio/src/gui/colorlcd/setup_menus/pagegroup.cpp @@ -193,7 +193,8 @@ void PageGroupHeaderBase::setTitle(const char* title) { if (titleLabel) { #if VERSION_MAJOR == 2 - std::string s = replaceAll(title, "\n", " "); + std::string s(title); + strReplaceAll(s, "\n", " "); lv_label_set_text(titleLabel, s.c_str()); #else lv_label_set_text(titleLabel, title); diff --git a/radio/src/gui/colorlcd/setup_menus/quick_menu.cpp b/radio/src/gui/colorlcd/setup_menus/quick_menu.cpp index 3a6cf3cb2..095b8fd90 100644 --- a/radio/src/gui/colorlcd/setup_menus/quick_menu.cpp +++ b/radio/src/gui/colorlcd/setup_menus/quick_menu.cpp @@ -452,18 +452,6 @@ int QuickMenu::pageIndex(QMPage page) return 0; } -std::string replaceAll(std::string str, const std::string& from, const std::string& to) -{ - auto&& pos = str.find(from, size_t{}); - while (pos != std::string::npos) - { - str.replace(pos, from.length(), to); - // easy to forget to add to.length() - pos = str.find(from, pos + to.length()); - } - return str; -} - std::vector& QuickMenu::menuPageNames(bool forFavorites) { static std::vector qmPages; @@ -484,7 +472,7 @@ std::vector& QuickMenu::menuPageNames(bool forFavorites) s += STR_CURRENT_SCREEN; else s += STR_VAL(sub[j].title); - s = replaceAll(s, "\n", " "); + strReplaceAll(s, "\n", " "); qmPages.emplace_back(s); } } diff --git a/radio/src/gui/colorlcd/setup_menus/quick_menu.h b/radio/src/gui/colorlcd/setup_menus/quick_menu.h index 53f1ab0c7..749117325 100644 --- a/radio/src/gui/colorlcd/setup_menus/quick_menu.h +++ b/radio/src/gui/colorlcd/setup_menus/quick_menu.h @@ -61,10 +61,6 @@ extern const QMMainDef qmTopItems[]; //----------------------------------------------------------------------------- -std::string replaceAll(std::string str, const std::string& from, const std::string& to); - -//----------------------------------------------------------------------------- - #define GRP_W(n) ((QuickMenu::QM_BUTTON_WIDTH + QuickMenu::QM_HPAD) * n - QuickMenu::QM_HPAD + PAD_OUTLINE * 2) #define GRP_H(n) ((QuickMenu::QM_BUTTON_HEIGHT + QuickMenu::QM_VPAD) * n - QuickMenu::QM_VPAD + PAD_OUTLINE * 2) diff --git a/radio/src/storage/modelslist.cpp b/radio/src/storage/modelslist.cpp index f11b45849..1d0914a60 100644 --- a/radio/src/storage/modelslist.cpp +++ b/radio/src/storage/modelslist.cpp @@ -487,45 +487,25 @@ LabelsVector ModelMap::fromCSV(const char* str) // TODO - Fix me, ideally there should be no limitations void ModelMap::escapeCSV(std::string &str) { - replace_all(str, "/", "//"); - replace_all(str, ",", "/c"); + strReplaceAll(str, "/", "//"); + strReplaceAll(str, ",", "/c"); } // TODO - Fix me, ideally there should be no limitations void ModelMap::unEscapeCSV(std::string &str) { - replace_all(str, "//", "/"); - replace_all(str, "/c", ","); + strReplaceAll(str, "//", "/"); + strReplaceAll(str, "/c", ","); } // TODO - Fix me, ideally there should be no limitations void ModelMap::removeYAMLChars(std::string &str) { - replace_all(str, "\\", ""); - replace_all(str, "\"", ""); - replace_all(str, ":", ""); - replace_all(str, "\'", ""); - replace_all(str, "-", ""); -} - -/** - * @brief Replace all occurances of to in - * - * @param str String - * @param from String to search - * @param to String to replace - */ - -void ModelMap::replace_all(std::string &str, - const std::string &from, - const std::string &to) -{ - if(from.empty()) return; - size_t pos = 0; - while((pos = str.find(from, pos)) != std::string::npos) { - str.replace(pos, from.length(), to); - pos += to.length(); - } + strReplaceAll(str, "\\", ""); + strReplaceAll(str, "\"", ""); + strReplaceAll(str, ":", ""); + strReplaceAll(str, "\'", ""); + strReplaceAll(str, "-", ""); } /** @@ -756,7 +736,7 @@ bool ModelMap::renameLabel(const std::string &from, std::string to, std::string ModelMap::getBulletLabelString(ModelCell *curmod, const char *noresults) { std::string lbls = ModelMap::toCSV(getLabelsByModel(curmod)); - replace_all(lbls, ",", "\u2022"); + strReplaceAll(lbls, ",", "\u2022"); unEscapeCSV(lbls); if(lbls.size() == 0) { diff --git a/radio/src/storage/modelslist.h b/radio/src/storage/modelslist.h index d06934442..58146ec11 100644 --- a/radio/src/storage/modelslist.h +++ b/radio/src/storage/modelslist.h @@ -154,9 +154,6 @@ class ModelMap : protected std::multimap static void escapeCSV(std::string &str); static void unEscapeCSV(std::string &str); static void removeYAMLChars(std::string &str); - static void replace_all(std::string &str, - const std::string &from, - const std::string &to); void clear() { diff --git a/radio/src/strhelpers.cpp b/radio/src/strhelpers.cpp index ec16dcb34..bf20484c1 100644 --- a/radio/src/strhelpers.cpp +++ b/radio/src/strhelpers.cpp @@ -1314,3 +1314,14 @@ int timezoneOffsetSeconds(int8_t tzHour, int8_t tzMinute) { return (tzHour * 3600) + (tzMinute * 15 * 60); } + +void strReplaceAll(std::string &str, const std::string &from, + const std::string &to) +{ + if (from.empty()) return; + size_t pos = 0; + while ((pos = str.find(from, pos)) != std::string::npos) { + str.replace(pos, from.length(), to); + pos += to.length(); + } +} diff --git a/radio/src/strhelpers.h b/radio/src/strhelpers.h index 67632ad68..2b972d74e 100644 --- a/radio/src/strhelpers.h +++ b/radio/src/strhelpers.h @@ -208,6 +208,10 @@ std::string getTelemTime(TelemetryItem &telemetryItem); int countDigits(int number); +// Replace all occurrences of 'from' with 'to' in 'str', in place. +void strReplaceAll(std::string &str, const std::string &from, + const std::string &to); + // Timezone handling extern int8_t minTimezone(); extern int8_t maxTimezone(); diff --git a/radio/src/tests/strhelpers.cpp b/radio/src/tests/strhelpers.cpp new file mode 100644 index 000000000..b5915d6ff --- /dev/null +++ b/radio/src/tests/strhelpers.cpp @@ -0,0 +1,65 @@ +/* + * Copyright (C) EdgeTX + * + * Based on code named + * opentx - https://github.com/opentx/opentx + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "gtests.h" +#include "strhelpers.h" + +TEST(StrHelpers, ReplaceAllEmptyFrom) +{ + std::string s = "hello world"; + strReplaceAll(s, "", "x"); + EXPECT_EQ(s, "hello world"); +} + +TEST(StrHelpers, ReplaceAllEmptyTo) +{ + std::string s = "hello world"; + strReplaceAll(s, "o", ""); + EXPECT_EQ(s, "hell wrld"); +} + +TEST(StrHelpers, ReplaceAllNoMatch) +{ + std::string s = "hello world"; + strReplaceAll(s, "xyz", "abc"); + EXPECT_EQ(s, "hello world"); +} + +TEST(StrHelpers, ReplaceAllOverlappingMatches) +{ + std::string s = "aaaa"; + strReplaceAll(s, "aa", "a"); + EXPECT_EQ(s, "aa"); +} + +TEST(StrHelpers, ReplaceAllToContainsFrom) +{ + std::string s = "cat"; + strReplaceAll(s, "cat", "concatenate"); + EXPECT_EQ(s, "concatenate"); +} + +TEST(StrHelpers, ReplaceAllMultipleMatches) +{ + std::string s = "a,b,c,d"; + strReplaceAll(s, ",", " - "); + EXPECT_EQ(s, "a - b - c - d"); +}