mirror of
https://github.com/hyprwm/hyprlang.git
synced 2024-11-16 18:25:57 +01:00
core: fix dynamic variable updates with special categories
This commit is contained in:
parent
11d5ccda07
commit
bf5c561905
4 changed files with 51 additions and 20 deletions
|
@ -276,21 +276,32 @@ CParseResult CConfig::configSetValueSafe(const std::string& command, const std::
|
||||||
if (VALUEIT == impl->values.end()) {
|
if (VALUEIT == impl->values.end()) {
|
||||||
// it might be in a special category
|
// it might be in a special category
|
||||||
bool found = false;
|
bool found = false;
|
||||||
for (auto& sc : impl->specialCategories) {
|
|
||||||
if (!valueName.starts_with(sc->name))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (!sc->isStatic && std::string{std::any_cast<const char*>(sc->values[sc->key].getValue())} != impl->currentSpecialKey)
|
if (impl->currentSpecialCategory && valueName.starts_with(impl->currentSpecialCategory->name)) {
|
||||||
continue;
|
VALUEIT = impl->currentSpecialCategory->values.find(valueName.substr(impl->currentSpecialCategory->name.length() + 1));
|
||||||
|
|
||||||
VALUEIT = sc->values.find(valueName.substr(sc->name.length() + 1));
|
if (VALUEIT != impl->currentSpecialCategory->values.end())
|
||||||
|
|
||||||
if (VALUEIT != sc->values.end())
|
|
||||||
found = true;
|
found = true;
|
||||||
else if (sc->descriptor->dontErrorOnMissing)
|
}
|
||||||
return result; // will return a success, cuz we want to ignore missing
|
|
||||||
|
|
||||||
break;
|
if (!found) {
|
||||||
|
for (auto& sc : impl->specialCategories) {
|
||||||
|
if (!valueName.starts_with(sc->name))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (!sc->isStatic && std::string{std::any_cast<const char*>(sc->values[sc->key].getValue())} != impl->currentSpecialKey)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
VALUEIT = sc->values.find(valueName.substr(sc->name.length() + 1));
|
||||||
|
impl->currentSpecialCategory = sc.get();
|
||||||
|
|
||||||
|
if (VALUEIT != sc->values.end())
|
||||||
|
found = true;
|
||||||
|
else if (sc->descriptor->dontErrorOnMissing)
|
||||||
|
return result; // will return a success, cuz we want to ignore missing
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!found) {
|
if (!found) {
|
||||||
|
@ -312,7 +323,8 @@ CParseResult CConfig::configSetValueSafe(const std::string& command, const std::
|
||||||
|
|
||||||
applyDefaultsToCat(*PCAT);
|
applyDefaultsToCat(*PCAT);
|
||||||
|
|
||||||
VALUEIT = PCAT->values.find(valueName.substr(sc->name.length() + 1));
|
VALUEIT = PCAT->values.find(valueName.substr(sc->name.length() + 1));
|
||||||
|
impl->currentSpecialCategory = PCAT;
|
||||||
|
|
||||||
if (VALUEIT != PCAT->values.end())
|
if (VALUEIT != PCAT->values.end())
|
||||||
found = true;
|
found = true;
|
||||||
|
@ -421,8 +433,12 @@ CParseResult CConfig::parseVariable(const std::string& lhs, const std::string& r
|
||||||
|
|
||||||
if (dynamic) {
|
if (dynamic) {
|
||||||
for (auto& l : IT->linesContainingVar) {
|
for (auto& l : IT->linesContainingVar) {
|
||||||
parseLine(l, true);
|
impl->categories = l.categories;
|
||||||
|
impl->currentSpecialCategory = l.specialCategory;
|
||||||
|
parseLine(l.line, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl->categories = {};
|
||||||
}
|
}
|
||||||
|
|
||||||
CParseResult result;
|
CParseResult result;
|
||||||
|
@ -492,7 +508,7 @@ CParseResult CConfig::parseLine(std::string line, bool dynamic) {
|
||||||
if (RHSIT == std::string::npos && LHSIT == std::string::npos)
|
if (RHSIT == std::string::npos && LHSIT == std::string::npos)
|
||||||
continue;
|
continue;
|
||||||
else
|
else
|
||||||
var.linesContainingVar.push_back(line);
|
var.linesContainingVar.push_back({line, impl->categories, impl->currentSpecialCategory});
|
||||||
|
|
||||||
anyMatch = true;
|
anyMatch = true;
|
||||||
}
|
}
|
||||||
|
@ -537,7 +553,8 @@ CParseResult CConfig::parseLine(std::string line, bool dynamic) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
impl->currentSpecialKey = "";
|
impl->currentSpecialKey = "";
|
||||||
|
impl->currentSpecialCategory = nullptr;
|
||||||
impl->categories.pop_back();
|
impl->categories.pop_back();
|
||||||
} else {
|
} else {
|
||||||
// open a category.
|
// open a category.
|
||||||
|
|
|
@ -11,9 +11,16 @@ struct SHandler {
|
||||||
};
|
};
|
||||||
|
|
||||||
struct SVariable {
|
struct SVariable {
|
||||||
std::string name = "";
|
std::string name = "";
|
||||||
std::string value = "";
|
std::string value = "";
|
||||||
std::vector<std::string> linesContainingVar; // for dynamic updates
|
|
||||||
|
struct SVarLine {
|
||||||
|
std::string line;
|
||||||
|
std::vector<std::string> categories;
|
||||||
|
SSpecialCategory* specialCategory = nullptr; // if applicable
|
||||||
|
};
|
||||||
|
|
||||||
|
std::vector<SVarLine> linesContainingVar; // for dynamic updates
|
||||||
};
|
};
|
||||||
|
|
||||||
// remember to also edit CConfigValue if editing
|
// remember to also edit CConfigValue if editing
|
||||||
|
@ -71,7 +78,8 @@ class CConfigImpl {
|
||||||
std::vector<std::unique_ptr<SSpecialCategoryDescriptor>> specialCategoryDescriptors;
|
std::vector<std::unique_ptr<SSpecialCategoryDescriptor>> specialCategoryDescriptors;
|
||||||
|
|
||||||
std::vector<std::string> categories;
|
std::vector<std::string> categories;
|
||||||
std::string currentSpecialKey = "";
|
std::string currentSpecialKey = "";
|
||||||
|
SSpecialCategory* currentSpecialCategory = nullptr; // if applicable
|
||||||
|
|
||||||
std::string parseError = "";
|
std::string parseError = "";
|
||||||
|
|
||||||
|
|
|
@ -31,9 +31,11 @@ testCategory {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$SPECIALVAL1 = 1
|
||||||
|
|
||||||
special {
|
special {
|
||||||
key = a
|
key = a
|
||||||
value = 1
|
value = $SPECIALVAL1
|
||||||
}
|
}
|
||||||
|
|
||||||
special {
|
special {
|
||||||
|
|
|
@ -191,6 +191,10 @@ int main(int argc, char** argv, char** envp) {
|
||||||
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:one", "value")), 1);
|
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:one", "value")), 1);
|
||||||
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:two", "value")), 2);
|
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:two", "value")), 2);
|
||||||
|
|
||||||
|
// test dynamic special variable
|
||||||
|
EXPECT(config.parseDynamic("$SPECIALVAL1 = 2").error, false);
|
||||||
|
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("special", "value", "a")), (Hyprlang::INT)2);
|
||||||
|
|
||||||
// test copying
|
// test copying
|
||||||
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:one", "copyTest")), 2);
|
EXPECT(std::any_cast<int64_t>(config.getSpecialConfigValue("specialGeneric:one", "copyTest")), 2);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue