Skip to content

Commit

Permalink
InputCommon: fix serialization of control expression with line breaks
Browse files Browse the repository at this point in the history
The control expression editor allows line breaks, but the serialization was
losing anything after the first line break (/r /n).
Instead of opting to encode them and decode them on serialization
(which I tried but was not safe, as it would lose /n written in the string by users),
I opted to replace them with a space.
  • Loading branch information
Filoppi committed May 12, 2021
1 parent eb5cd9b commit 5744778
Show file tree
Hide file tree
Showing 4 changed files with 25 additions and 4 deletions.
9 changes: 8 additions & 1 deletion Source/Core/Common/StringUtil.cpp
Expand Up @@ -219,7 +219,7 @@ std::string ArrayToString(const u8* data, u32 size, int line_len, bool spaces)
return oss.str();
}

// Turns " hello " into "hello". Also handles tabs.
// Turns "\n\r\t hello " into "hello" (trims at the start and end but not inside).
std::string_view StripSpaces(std::string_view str)
{
const size_t s = str.find_first_not_of(" \t\r\n");
Expand All @@ -241,6 +241,13 @@ std::string_view StripQuotes(std::string_view s)
return s;
}

// Turns "\n\rhello" into " hello".
void ReplaceBreaksWithSpaces(std::string& str)
{
std::replace(str.begin(), str.end(), '\r', ' ');
std::replace(str.begin(), str.end(), '\n', ' ');
}

bool TryParse(const std::string& str, bool* const output)
{
float value;
Expand Down
2 changes: 2 additions & 0 deletions Source/Core/Common/StringUtil.h
Expand Up @@ -52,6 +52,8 @@ std::string_view StripQuotes(std::string_view s);

std::string ReplaceAll(std::string result, std::string_view src, std::string_view dest);

void ReplaceBreaksWithSpaces(std::string& str);

bool TryParse(const std::string& str, bool* output);

template <typename T, std::enable_if_t<std::is_integral_v<T> || std::is_enum_v<T>>* = nullptr>
Expand Down
Expand Up @@ -117,7 +117,10 @@ void ControlGroup::SaveConfig(IniFile::Section* sec, const std::string& defdev,
for (auto& c : controls)
{
// control expression
sec->Set(group + c->name, c->control_ref->GetExpression(), "");
std::string expression = c->control_ref->GetExpression();
// We can't save line breaks in a single line config. Restoring them is too complicated.
ReplaceBreaksWithSpaces(expression);
sec->Set(group + c->name, expression, "");

// range
sec->Set(group + c->name + "/Range", c->control_ref->range * 100.0, 100.0);
Expand All @@ -135,7 +138,9 @@ void ControlGroup::SaveConfig(IniFile::Section* sec, const std::string& defdev,
}
else
{
sec->Set(base + name, ext->GetSelectionSetting().GetInputReference().GetExpression(), "None");
std::string expression = ext->GetSelectionSetting().GetInputReference().GetExpression();
ReplaceBreaksWithSpaces(expression);
sec->Set(base + name, expression, "None");
}

for (auto& ai : ext->GetAttachmentList())
Expand Down
Expand Up @@ -113,9 +113,16 @@ class NumericSetting final : public NumericSettingBase
void SaveToIni(IniFile::Section& section, const std::string& group_name) const override
{
if (IsSimpleValue())
{
section.Set(group_name + m_details.ini_name, GetValue(), m_default_value);
}
else
section.Set(group_name + m_details.ini_name, m_value.m_input.GetExpression(), "");
{
// We can't save line breaks in a single line config. Restoring them is too complicated.
std::string expression = m_value.m_input.GetExpression();
ReplaceBreaksWithSpaces(expression);
section.Set(group_name + m_details.ini_name, expression, "");
}
}

bool IsSimpleValue() const override { return m_value.IsSimpleValue(); }
Expand Down

0 comments on commit 5744778

Please sign in to comment.