From 090dcb22ea82e4feb56d56eaab87597732fea593 Mon Sep 17 00:00:00 2001 From: vaxerski Date: Fri, 29 Dec 2023 11:22:24 +0100 Subject: [PATCH] core: add dynamic handlers --- src/config.cpp | 21 ++++++++++++++++++--- src/public.hpp | 14 +++++++++++++- tests/config/config.conf | 4 +++- tests/main.cpp | 27 ++++++++++++++++++++++++--- 4 files changed, 58 insertions(+), 8 deletions(-) diff --git a/src/config.cpp b/src/config.cpp index 1e32882..4ac3e1b 100644 --- a/src/config.cpp +++ b/src/config.cpp @@ -55,7 +55,7 @@ void CConfig::commence() { } } -bool isNumber(const std::string& str, bool allowfloat) { +static bool isNumber(const std::string& str, bool allowfloat) { std::string copy = str; if (*copy.begin() == '-') @@ -80,7 +80,7 @@ bool isNumber(const std::string& str, bool allowfloat) { return true; } -int64_t configStringToInt(const std::string& VALUE) { +static int64_t configStringToInt(const std::string& VALUE) { if (VALUE.starts_with("0x")) { // Values with 0x are hex const auto VALUEWITHOUTHEX = VALUE.substr(2); @@ -300,7 +300,7 @@ CParseResult CConfig::parse() { if (!m_bCommenced) throw "Cannot parse: not commenced. You have to .commence() first."; - impl->parseError = ""; + clearState(); for (auto& [k, v] : impl->defaultValues) { impl->values.at(k) = v; @@ -329,9 +329,24 @@ CParseResult CConfig::parse() { iffile.close(); + clearState(); + return fileParseResult; } +CParseResult CConfig::parseDynamic(const char* line) { + return parseLine(line); +} + +CParseResult CConfig::parseDynamic(const char* command, const char* value) { + return parseLine(std::string{command} + "=" + std::string{value}); +} + +void CConfig::clearState() { + impl->categories.clear(); + impl->parseError = ""; +} + CConfigValue* CConfig::getConfigValuePtr(const char* name) { const auto IT = impl->values.find(std::string{name}); return IT == impl->values.end() ? nullptr : &IT->second; diff --git a/src/public.hpp b/src/public.hpp index 2c144f9..58e41df 100644 --- a/src/public.hpp +++ b/src/public.hpp @@ -24,10 +24,15 @@ namespace Hyprlang { class CParseResult { public: - bool error = false; + bool error = false; + /* Get this ParseResult's error string. + Pointer valid until the error string is changed or this + object gets destroyed. */ const char* getError() const { return errorString; } + /* Set an error contained by this ParseResult. + Creates a copy of the string, does not take ownership. */ void setError(const char* err); private: @@ -109,6 +114,12 @@ namespace Hyprlang { /* Parse the config. Refresh the values. */ CParseResult parse(); + /* Parse a single "line", dynamically. + Values set by this are temporary and will be overwritten + by default / config on the next parse() */ + CParseResult parseDynamic(const char* line); + CParseResult parseDynamic(const char* command, const char* value); + /* Get a config's value ptr. These are static. nullptr on fail */ CConfigValue* getConfigValuePtr(const char* name); @@ -128,5 +139,6 @@ namespace Hyprlang { CParseResult parseLine(std::string line); CParseResult configSetValueSafe(const std::string& command, const std::string& value); + void clearState(); }; }; \ No newline at end of file diff --git a/tests/config/config.conf b/tests/config/config.conf index 75a2b0d..28402b4 100644 --- a/tests/config/config.conf +++ b/tests/config/config.conf @@ -7,7 +7,7 @@ testString = Hello World! ## This is not a comment! # This is! testCategory { testValueInt = 123456 - testValueHex = 0xFFFFaabb + testValueHex = 0xF testColor1 = rgb(255, 255, 255) testColor2 = rgba(0, 0, 0, 1.0) @@ -21,6 +21,8 @@ testCategory { } } +testCategory:testValueHex = 0xFFfFaAbB + testStringQuotes = "Hello World!" #testDefault = 123 diff --git a/tests/main.cpp b/tests/main.cpp index 52ea912..e38a4e6 100644 --- a/tests/main.cpp +++ b/tests/main.cpp @@ -2,12 +2,22 @@ #include +namespace Colors { + constexpr const char* RED = "\x1b[31m"; + constexpr const char* GREEN = "\x1b[32m"; + constexpr const char* YELLOW = "\x1b[33m"; + constexpr const char* BLUE = "\x1b[34m"; + constexpr const char* MAGENTA = "\x1b[35m"; + constexpr const char* CYAN = "\x1b[36m"; + constexpr const char* RESET = "\x1b[0m"; +}; + #define EXPECT(expr, val) \ if (const auto RESULT = expr; RESULT != (val)) { \ - std::cout << "Failed: " << #expr << ", expected " << #val << " but got " << RESULT << "\n"; \ + std::cout << Colors::RED << "Failed: " << Colors::RESET << #expr << ", expected " << #val << " but got " << RESULT << "\n"; \ ret = 1; \ } else { \ - std::cout << "Passed " << #expr << ". Got " << val << "\n"; \ + std::cout << Colors::GREEN << "Passed " << Colors::RESET << #expr << ". Got " << val << "\n"; \ } // globals for testing @@ -67,6 +77,7 @@ int main(int argc, char** argv, char** envp) { EXPECT(PARSERESULT.error, false); // test values + std::cout << " → Testing values\n"; EXPECT(std::any_cast(config.getConfigValue("testInt")), 123); EXPECT(std::any_cast(config.getConfigValue("testFloat")), 123.456f); auto EXP = Hyprlang::SVector2D{69, 420}; @@ -83,10 +94,20 @@ int main(int argc, char** argv, char** envp) { EXPECT(std::any_cast(config.getConfigValue("testCategory:testColor3")), 0x22ffeeffL); // test handlers + std::cout << " → Testing handlers\n"; EXPECT(barrelRoll, true); EXPECT(flagsFound, std::string{"abc"}); + + // test dynamic + std::cout << " → Testing dynamic\n"; + barrelRoll = false; + EXPECT(config.parseDynamic("doABarrelRoll = woohoo, some, params").error, false); + EXPECT(barrelRoll, true); + EXPECT(config.parseDynamic("testCategory:testValueHex", "0xaabbccdd").error, false); + EXPECT(std::any_cast(config.getConfigValue("testCategory:testValueHex")), 0xAABBCCDDL); + } catch (const char* e) { - std::cout << "Error: " << e << "\n"; + std::cout << Colors::RED << "Error: " << Colors::RESET << e << "\n"; return 1; }