From d5ee21079756ce92aaae06d4856b7e3242eea31d Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 12 Feb 2017 21:11:28 +0000 Subject: [PATCH 01/50] Begin writing IniReader --- src/openrct2/config.c | 4 +- src/openrct2/config/IniReader.cpp | 140 ++++++++++++++++++++++++++++++ src/openrct2/config/IniReader.h | 1 + src/openrct2/core/String.cpp | 40 +++++++++ src/openrct2/core/String.hpp | 1 + src/openrct2/libopenrct2.vcxproj | 2 + 6 files changed, 186 insertions(+), 2 deletions(-) create mode 100644 src/openrct2/config/IniReader.cpp create mode 100644 src/openrct2/config/IniReader.h diff --git a/src/openrct2/config.c b/src/openrct2/config.c index b329f66bc8..3368fe5cb0 100644 --- a/src/openrct2/config.c +++ b/src/openrct2/config.c @@ -338,7 +338,7 @@ network_configuration gConfigNetwork; notification_configuration gConfigNotifications; font_configuration gConfigFonts; -static bool config_open(const utf8string path); +bool config_open(const utf8string path); static bool config_save(const utf8string path); static void config_read_properties(config_section_definition **currentSection, const_utf8string line); static void config_save_property_value(SDL_RWops *file, uint8 type, value_union *value); @@ -500,7 +500,7 @@ bool config_save_default() return false; } -bool config_open(const utf8string path) +bool config_open_2(const utf8string path) { SDL_RWops *file; utf8string lineBuffer; diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp new file mode 100644 index 0000000000..454abe3098 --- /dev/null +++ b/src/openrct2/config/IniReader.cpp @@ -0,0 +1,140 @@ +#include +#include +#include +#include +#include "../common.h" +#include "../core/FileStream.hpp" +#include "../core/String.hpp" + +class ConfigEnum +{ + +}; + +class IniReader +{ +private: + std::vector _buffer; + std::vector> _lines; + std::unordered_map _sections; + +public: + IniReader(const std::string &path) + { + auto fs = FileStream(path, FILE_MODE_OPEN); + uint64 length = fs.GetLength(); + _buffer.resize(length); + fs.Read(_buffer.data(), length); + + RemoveBOM(); + + // Ensure there is a null terminator on the end, this is + // mainly for ParseLines's sake + if (_buffer[length - 1] != 0) + { + _buffer.push_back(0); + } + + ParseLines(); + ParseSections(); + } + + bool ReadSection(const std::string &name) + { + auto it = _sections.find(name); + if (it == _sections.end()) + { + return false; + } + + size_t startLine = it->second; + UNUSED(startLine); + return true; + } + + bool GetBoolean(const std::string &name, bool defaultValue) + { + + } + + sint32 GetSint32(const std::string &name, sint32 defaultValue, const ConfigEnum * configEnum = nullptr) + { + + } + + std::string GetString(const std::string &name, const std::string &defaultValue) + { + + } + +private: + void RemoveBOM() + { + utf8 * file = (utf8 *)_buffer.data(); + utf8 * content = String::SkipBOM(file); + if (file != content) + { + size_t skipLength = content - file; + _buffer.erase(_buffer.begin(), _buffer.begin() + skipLength); + } + } + + void ParseLines() + { + size_t lineBegin = 0; + bool onNewLineCh = false; + for (size_t i = 0; i < _buffer.size(); i++) + { + char b = (char)_buffer[i]; + if (b == 0 || b == '\n' || b == '\r') + { + if (!onNewLineCh) + { + onNewLineCh = true; + size_t lineEnd = i; + _lines.emplace_back(lineBegin, lineEnd - lineBegin); + } + } + else if (onNewLineCh) + { + onNewLineCh = false; + lineBegin = i; + } + } + } + + void ParseSections() + { + for (size_t i = 0; i < _lines.size(); i++) + { + std::string line = GetLine(i); + line = String::Trim(line); + if (line.size() > 3 && line[0] == '[') + { + size_t endIndex = line.find_first_of(']'); + std::string sectionName = line.substr(1, endIndex - 1); + _sections[sectionName] = i; + } + } + } + + std::string GetLine(size_t index) + { + utf8 * szBuffer = (utf8 *)_buffer.data(); + auto span = _lines[index]; + auto line = std::string(szBuffer + std::get<0>(span), std::get<1>(span)); + return line; + } +}; + +extern "C" +{ + bool config_open(const utf8 * path) + { + auto iniReader = IniReader(path); + bool b = iniReader.ReadSection("general"); + UNUSED(b); + + return false; + } +} diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.h new file mode 100644 index 0000000000..6f70f09bee --- /dev/null +++ b/src/openrct2/config/IniReader.h @@ -0,0 +1 @@ +#pragma once diff --git a/src/openrct2/core/String.cpp b/src/openrct2/core/String.cpp index 68c9ad85ba..bc8a0035a7 100644 --- a/src/openrct2/core/String.cpp +++ b/src/openrct2/core/String.cpp @@ -393,4 +393,44 @@ namespace String { return String::Set(buffer, bufferSize, TrimStart(src)); } + + std::string Trim(const std::string &s) + { + const utf8 * firstNonWhitespace = nullptr; + + codepoint_t codepoint; + const utf8 * ch = s.c_str(); + const utf8 * nextCh; + while ((codepoint = GetNextCodepoint(ch, &nextCh)) != '\0') + { + bool isWhiteSpace = codepoint <= WCHAR_MAX && iswspace((wchar_t)codepoint); + if (isWhiteSpace) + { + if (firstNonWhitespace != nullptr) + { + break; + } + } + else + { + if (firstNonWhitespace == nullptr) + { + firstNonWhitespace = ch; + } + } + ch = nextCh; + } + + if (firstNonWhitespace != nullptr && + firstNonWhitespace != s.c_str()) + { + size_t newStringSize = ch - firstNonWhitespace; + return std::string(firstNonWhitespace, newStringSize); + } + else + { + size_t newStringSize = ch - s.c_str(); + return std::string(s.c_str(), newStringSize); + } + } } diff --git a/src/openrct2/core/String.hpp b/src/openrct2/core/String.hpp index 287c1c3cd0..427374b2af 100644 --- a/src/openrct2/core/String.hpp +++ b/src/openrct2/core/String.hpp @@ -75,4 +75,5 @@ namespace String utf8 * Trim(utf8 * str); const utf8 * TrimStart(const utf8 * str); utf8 * TrimStart(utf8 * buffer, size_t bufferSize, const utf8 * src); + std::string Trim(const std::string &s); } diff --git a/src/openrct2/libopenrct2.vcxproj b/src/openrct2/libopenrct2.vcxproj index 601b403f64..c842c27096 100644 --- a/src/openrct2/libopenrct2.vcxproj +++ b/src/openrct2/libopenrct2.vcxproj @@ -72,6 +72,7 @@ + @@ -419,6 +420,7 @@ + From f8f60a69a7c39f147213328198a2357931f43deb Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 12 Feb 2017 21:44:56 +0000 Subject: [PATCH 02/50] Implement reading of config values --- src/openrct2/config/IniReader.cpp | 138 +++++++++++++++++++++++++++--- 1 file changed, 125 insertions(+), 13 deletions(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 454abe3098..c7eddeae13 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -11,12 +11,39 @@ class ConfigEnum }; +struct Span +{ + size_t Start = 0; + size_t Length = 0; + + Span() = default; + Span(size_t start, size_t length) + : Start(start), + Length(length) + { + } +}; + +struct LineRange +{ + size_t Start = 0; + size_t End = 0; + + LineRange() = default; + LineRange(size_t start, size_t end) + : Start(start), + End(end) + { + } +}; + class IniReader { private: - std::vector _buffer; - std::vector> _lines; - std::unordered_map _sections; + std::vector _buffer; + std::vector _lines; + std::unordered_map _sections; + std::unordered_map _values; public: IniReader(const std::string &path) @@ -47,24 +74,43 @@ public: return false; } - size_t startLine = it->second; - UNUSED(startLine); + ParseValues(it->second); return true; } bool GetBoolean(const std::string &name, bool defaultValue) { + auto it = _values.find(name); + if (it == _values.end()) + { + return defaultValue; + } + std::string value = it->second; + return String::Equals(value, "true", true); } sint32 GetSint32(const std::string &name, sint32 defaultValue, const ConfigEnum * configEnum = nullptr) { + auto it = _values.find(name); + if (it == _values.end()) + { + return defaultValue; + } + std::string value = it->second; + return std::stoi(value); } std::string GetString(const std::string &name, const std::string &defaultValue) { + auto it = _values.find(name); + if (it == _values.end()) + { + return defaultValue; + } + return it->second; } private: @@ -105,6 +151,9 @@ private: void ParseSections() { + std::string sectionName; + LineRange lineRange; + for (size_t i = 0; i < _lines.size(); i++) { std::string line = GetLine(i); @@ -112,29 +161,92 @@ private: if (line.size() > 3 && line[0] == '[') { size_t endIndex = line.find_first_of(']'); - std::string sectionName = line.substr(1, endIndex - 1); - _sections[sectionName] = i; + if (endIndex != std::string::npos) + { + // Add last section + if (!sectionName.empty()) + { + lineRange.End = i - 1; + _sections[sectionName] = lineRange; + } + + // Set up new section + sectionName = line.substr(1, endIndex - 1); + lineRange.Start = i; + } } } + + // Add final section + if (!sectionName.empty()) + { + lineRange.End = _lines.size() - 1; + _sections[sectionName] = lineRange; + } + } + + void ParseValues(LineRange range) + { + for (size_t i = range.Start + 1; i <= range.End; i++) + { + ParseValue(i); + } + } + + void ParseValue(size_t lineIndex) + { + std::string line = GetLine(lineIndex); + + // Chop off comment + size_t hashIndex = line.find_first_of('#'); + if (hashIndex != std::string::npos) + { + line = line.substr(0, hashIndex); + } + + // Find assignment character + size_t equalsIndex = line.find_first_of('='); + if (equalsIndex == std::string::npos) + { + return; + } + + // Get the key and value + std::string key = String::Trim(line.substr(0, equalsIndex)); + std::string value = String::Trim(line.substr(equalsIndex + 1)); + + _values[key] = value; } std::string GetLine(size_t index) { utf8 * szBuffer = (utf8 *)_buffer.data(); auto span = _lines[index]; - auto line = std::string(szBuffer + std::get<0>(span), std::get<1>(span)); + auto line = std::string(szBuffer + span.Start, span.Length); return line; } }; extern "C" { + #include "../config.h" + bool config_open(const utf8 * path) { - auto iniReader = IniReader(path); - bool b = iniReader.ReadSection("general"); - UNUSED(b); - - return false; + try + { + auto iniReader = IniReader(path); + if (iniReader.ReadSection("general")) + { + gConfigGeneral.always_show_gridlines = iniReader.GetBoolean("always_show_gridlines", false); + gConfigGeneral.window_width = iniReader.GetSint32("window_width", -1); + gConfigGeneral.window_height = iniReader.GetSint32("window_height", -1); + } + return true; + } + catch (const Exception &) + { + return false; + } } } From 3255a1b88c10121cae7b66f4a4e0ed6f8633afdb Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 12 Feb 2017 22:23:27 +0000 Subject: [PATCH 03/50] Support reading quoted strings --- src/openrct2/config/IniReader.cpp | 77 +++++++++++++++++++++++++++---- 1 file changed, 68 insertions(+), 9 deletions(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index c7eddeae13..e3e0bbe588 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -5,6 +5,7 @@ #include "../common.h" #include "../core/FileStream.hpp" #include "../core/String.hpp" +#include "../core/StringBuilder.hpp" class ConfigEnum { @@ -74,7 +75,7 @@ public: return false; } - ParseValues(it->second); + ParseSectionValues(it->second); return true; } @@ -185,7 +186,7 @@ private: } } - void ParseValues(LineRange range) + void ParseSectionValues(LineRange range) { for (size_t i = range.Start + 1; i <= range.End; i++) { @@ -196,13 +197,7 @@ private: void ParseValue(size_t lineIndex) { std::string line = GetLine(lineIndex); - - // Chop off comment - size_t hashIndex = line.find_first_of('#'); - if (hashIndex != std::string::npos) - { - line = line.substr(0, hashIndex); - } + line = TrimComment(line); // Find assignment character size_t equalsIndex = line.find_first_of('='); @@ -215,9 +210,73 @@ private: std::string key = String::Trim(line.substr(0, equalsIndex)); std::string value = String::Trim(line.substr(equalsIndex + 1)); + value = UnquoteValue(value); + value = UnescapeValue(value); _values[key] = value; } + std::string TrimComment(const std::string &s) + { + char inQuotes = 0; + bool escaped = false; + for (size_t i = 0; i < s.size(); i++) + { + char c = s[i]; + if (inQuotes == 0 && c == '#' && !escaped) + { + return s.substr(0, i); + } + else if (c == inQuotes && !escaped) + { + inQuotes = 0; + } + else if (c == '\'' || c == '"' && !escaped) + { + inQuotes = c; + } + escaped = (c == '\\' && !escaped); + } + return s; + } + + std::string UnquoteValue(const std::string &s) + { + std::string result = s; + size_t length = s.size(); + if (length >= 2) + { + if ((s[0] == '"' || s[0] == '\'') && s[0] == s[length - 1]) + { + result = s.substr(1, length - 2); + } + } + return result; + } + + std::string UnescapeValue(const std::string &s) + { + if (s.find_first_of('\\') == std::string::npos) + { + return s; + } + + bool escaped = false; + auto sb = StringBuilder(); + for (char c : s) + { + if (c == '\\' && !escaped) + { + escaped = true; + } + else + { + escaped = false; + sb.Append(&c, 1); + } + } + return std::string(sb.GetString()); + } + std::string GetLine(size_t index) { utf8 * szBuffer = (utf8 *)_buffer.data(); From a582cc0ccac2e58296dbc6fbc5d8a561e7cdc0fa Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 12 Feb 2017 22:44:23 +0000 Subject: [PATCH 04/50] Add support for config enums --- src/openrct2/config/IniReader.cpp | 68 ++++++++++++++++++++++++++++++- 1 file changed, 67 insertions(+), 1 deletion(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index e3e0bbe588..ce9c67d900 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -1,3 +1,4 @@ +#include #include #include #include @@ -7,9 +8,54 @@ #include "../core/String.hpp" #include "../core/StringBuilder.hpp" +template +struct ConfigEnumEntry +{ + std::string Key; + T Value; + + ConfigEnumEntry(const std::string &key, T value) + : Key(key), + Value(value) + { + } +}; + +template class ConfigEnum { +private: + std::vector> _entries; +public: + ConfigEnum(std::initializer_list> entries) + { + _entries = entries; + } + + std::string GetName(T value) + { + for (const auto &entry : _entries) const + { + if (entry.Value == value) + { + return entry.Key; + } + } + return std::string(); + } + + T GetValue(const std::string &key, T defaultValue) const + { + for (const auto &entry : _entries) + { + if (String::Equals(entry.Key, key, true)) + { + return entry.Value; + } + } + return defaultValue; + } }; struct Span @@ -91,7 +137,7 @@ public: return String::Equals(value, "true", true); } - sint32 GetSint32(const std::string &name, sint32 defaultValue, const ConfigEnum * configEnum = nullptr) + sint32 GetSint32(const std::string &name, sint32 defaultValue) { auto it = _values.find(name); if (it == _values.end()) @@ -103,6 +149,18 @@ public: return std::stoi(value); } + template + T GetEnum(const std::string &name, T defaultValue, const ConfigEnum &configEnum) + { + auto it = _values.find(name); + if (it == _values.end()) + { + return defaultValue; + } + + return configEnum.GetValue(it->second, defaultValue); + } + std::string GetString(const std::string &name, const std::string &defaultValue) { auto it = _values.find(name); @@ -290,6 +348,13 @@ extern "C" { #include "../config.h" + auto Enum_MeasurementFormat = ConfigEnum( + { + ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), + ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), + ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), + }); + bool config_open(const utf8 * path) { try @@ -300,6 +365,7 @@ extern "C" gConfigGeneral.always_show_gridlines = iniReader.GetBoolean("always_show_gridlines", false); gConfigGeneral.window_width = iniReader.GetSint32("window_width", -1); gConfigGeneral.window_height = iniReader.GetSint32("window_height", -1); + gConfigGeneral.measurement_format = iniReader.GetEnum("measurement_format", MEASUREMENT_FORMAT_METRIC, Enum_MeasurementFormat); } return true; } From 6f15fc2cee6200002ad27b9f8846c7f698a99a4a Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 15 Feb 2017 20:52:50 +0000 Subject: [PATCH 05/50] Refactor config reading to different files --- src/openrct2/config/Config.cpp | 84 ++++++++++++++++++ src/openrct2/config/Config.h | 17 ++++ src/openrct2/config/ConfigEnum.h | 71 +++++++++++++++ src/openrct2/config/IniReader.cpp | 139 ++++++++++-------------------- src/openrct2/config/IniReader.h | 48 ++++++++++- src/openrct2/libopenrct2.vcxproj | 3 + 6 files changed, 267 insertions(+), 95 deletions(-) create mode 100644 src/openrct2/config/Config.cpp create mode 100644 src/openrct2/config/Config.h create mode 100644 src/openrct2/config/ConfigEnum.h diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp new file mode 100644 index 0000000000..fde86fe57f --- /dev/null +++ b/src/openrct2/config/Config.cpp @@ -0,0 +1,84 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#include +#include "../core/Exception.hpp" +#include "IniReader.h" + +extern "C" +{ + #include "../config.h" +} + +namespace Config +{ + static auto Enum_MeasurementFormat = ConfigEnum( + { + ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), + ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), + ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), + }); + + static void ReadGeneral(IIniReader * reader) + { + if (reader->ReadSection("general")) + { + gConfigGeneral.always_show_gridlines = reader->GetBoolean("always_show_gridlines", false); + gConfigGeneral.window_width = reader->GetSint32("window_width", -1); + gConfigGeneral.window_height = reader->GetSint32("window_height", -1); + gConfigGeneral.measurement_format = reader->GetEnum("measurement_format", MEASUREMENT_FORMAT_METRIC, Enum_MeasurementFormat); + } + } + + static void ReadSound(IIniReader * reader) + { + if (reader->ReadSection("sound")) + { + auto model = &gConfigSound; + model->master_volume = reader->GetSint32("master_volume", 100); + model->title_music = reader->GetSint32("title_music", 2); + model->sound_enabled = reader->GetBoolean("sound", true); + model->sound_volume = reader->GetSint32("sound_volume", 100); + model->ride_music_enabled = reader->GetBoolean("ride_music", true); + model->ride_music_volume = reader->GetSint32("ride_music_volume", 100); + model->audio_focus = reader->GetBoolean("audio_focus", false); + model->device = reader->GetCString("audio_device", nullptr); + } + } + + static bool ReadFile(const std::string &path) + { + try + { + auto reader = std::unique_ptr(CreateIniReader(path)); + ReadGeneral(reader.get()); + ReadSound(reader.get()); + return true; + } + catch (const Exception &) + { + return false; + } + } +} + +extern "C" +{ + bool config_open(const utf8 * path) + { + return Config::ReadFile(path); + } +} diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h new file mode 100644 index 0000000000..1ea5ab7cc9 --- /dev/null +++ b/src/openrct2/config/Config.h @@ -0,0 +1,17 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#pragma once diff --git a/src/openrct2/config/ConfigEnum.h b/src/openrct2/config/ConfigEnum.h new file mode 100644 index 0000000000..ef2013c338 --- /dev/null +++ b/src/openrct2/config/ConfigEnum.h @@ -0,0 +1,71 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#pragma once + +#include +#include +#include "../core/String.hpp" + +template +struct ConfigEnumEntry +{ + std::string Key; + T Value; + + ConfigEnumEntry(const std::string &key, T value) + : Key(key), + Value(value) + { + } +}; + +template +class ConfigEnum +{ +private: + std::vector> _entries; + +public: + ConfigEnum(std::initializer_list> entries) + { + _entries = entries; + } + + std::string GetName(T value) + { + for (const auto &entry : _entries) const + { + if (entry.Value == value) + { + return entry.Key; + } + } + return std::string(); + } + + T GetValue(const std::string &key, T defaultValue) const + { + for (const auto &entry : _entries) + { + if (String::Equals(entry.Key, key, true)) + { + return entry.Value; + } + } + return defaultValue; + } +}; diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index ce9c67d900..a04a1b7fd5 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -1,3 +1,19 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + #include #include #include @@ -7,56 +23,7 @@ #include "../core/FileStream.hpp" #include "../core/String.hpp" #include "../core/StringBuilder.hpp" - -template -struct ConfigEnumEntry -{ - std::string Key; - T Value; - - ConfigEnumEntry(const std::string &key, T value) - : Key(key), - Value(value) - { - } -}; - -template -class ConfigEnum -{ -private: - std::vector> _entries; - -public: - ConfigEnum(std::initializer_list> entries) - { - _entries = entries; - } - - std::string GetName(T value) - { - for (const auto &entry : _entries) const - { - if (entry.Value == value) - { - return entry.Key; - } - } - return std::string(); - } - - T GetValue(const std::string &key, T defaultValue) const - { - for (const auto &entry : _entries) - { - if (String::Equals(entry.Key, key, true)) - { - return entry.Value; - } - } - return defaultValue; - } -}; +#include "IniReader.h" struct Span { @@ -84,7 +51,7 @@ struct LineRange } }; -class IniReader +class IniReader final : public IIniReader { private: std::vector _buffer; @@ -113,7 +80,7 @@ public: ParseSections(); } - bool ReadSection(const std::string &name) + bool ReadSection(const std::string &name) override { auto it = _sections.find(name); if (it == _sections.end()) @@ -125,7 +92,7 @@ public: return true; } - bool GetBoolean(const std::string &name, bool defaultValue) + bool GetBoolean(const std::string &name, bool defaultValue) const override { auto it = _values.find(name); if (it == _values.end()) @@ -137,7 +104,7 @@ public: return String::Equals(value, "true", true); } - sint32 GetSint32(const std::string &name, sint32 defaultValue) + sint32 GetSint32(const std::string &name, sint32 defaultValue) const override { auto it = _values.find(name); if (it == _values.end()) @@ -149,19 +116,7 @@ public: return std::stoi(value); } - template - T GetEnum(const std::string &name, T defaultValue, const ConfigEnum &configEnum) - { - auto it = _values.find(name); - if (it == _values.end()) - { - return defaultValue; - } - - return configEnum.GetValue(it->second, defaultValue); - } - - std::string GetString(const std::string &name, const std::string &defaultValue) + std::string GetString(const std::string &name, const std::string &defaultValue) const override { auto it = _values.find(name); if (it == _values.end()) @@ -172,6 +127,18 @@ public: return it->second; } + bool TryGetString(const std::string &name, std::string * outValue) const override + { + auto it = _values.find(name); + if (it == _values.end()) + { + return false; + } + + *outValue = it->second; + return true; + } + private: void RemoveBOM() { @@ -344,34 +311,18 @@ private: } }; -extern "C" +utf8 * IIniReader::GetCString(const std::string &name, const utf8 * defaultValue) const { - #include "../config.h" - - auto Enum_MeasurementFormat = ConfigEnum( + std::string szValue; + if (!TryGetString(name, &szValue)) { - ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), - ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), - ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), - }); - - bool config_open(const utf8 * path) - { - try - { - auto iniReader = IniReader(path); - if (iniReader.ReadSection("general")) - { - gConfigGeneral.always_show_gridlines = iniReader.GetBoolean("always_show_gridlines", false); - gConfigGeneral.window_width = iniReader.GetSint32("window_width", -1); - gConfigGeneral.window_height = iniReader.GetSint32("window_height", -1); - gConfigGeneral.measurement_format = iniReader.GetEnum("measurement_format", MEASUREMENT_FORMAT_METRIC, Enum_MeasurementFormat); - } - return true; - } - catch (const Exception &) - { - return false; - } + return String::Duplicate(defaultValue); } + + return String::Duplicate(szValue.c_str()); +} + +IIniReader * CreateIniReader(const std::string &path) +{ + return new IniReader(path); } diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.h index 6f70f09bee..85dfc1b31d 100644 --- a/src/openrct2/config/IniReader.h +++ b/src/openrct2/config/IniReader.h @@ -1 +1,47 @@ -#pragma once +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#include +#include "../common.h" +#include "ConfigEnum.h" + +interface IIniReader +{ + virtual ~IIniReader() = default; + + virtual bool ReadSection(const std::string &name) abstract; + + virtual bool GetBoolean(const std::string &name, bool defaultValue) const abstract; + virtual sint32 GetSint32(const std::string &name, sint32 defaultValue) const abstract; + virtual std::string GetString(const std::string &name, const std::string &defaultValue) const abstract; + virtual bool TryGetString(const std::string &name, std::string * outValue) const abstract; + + template + T GetEnum(const std::string &name, T defaultValue, const ConfigEnum &configEnum) const + { + std::string szValue; + if (!TryGetString(name, &szValue)) + { + return defaultValue; + } + + return configEnum.GetValue(szValue, defaultValue); + } + + utf8 * GetCString(const std::string &name, const utf8 * defaultValue) const; +}; + +IIniReader * CreateIniReader(const std::string &path); diff --git a/src/openrct2/libopenrct2.vcxproj b/src/openrct2/libopenrct2.vcxproj index c842c27096..2cb0e509af 100644 --- a/src/openrct2/libopenrct2.vcxproj +++ b/src/openrct2/libopenrct2.vcxproj @@ -72,6 +72,7 @@ + @@ -420,6 +421,8 @@ + + From aee1222829374da30011940eeed2c627d8063f8a Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 15 Feb 2017 22:51:39 +0000 Subject: [PATCH 06/50] Read more config --- src/openrct2/config/Config.cpp | 66 ++++++++++++++++++++++++++++++++++ 1 file changed, 66 insertions(+) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index fde86fe57f..77a3676dab 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -16,6 +16,7 @@ #include #include "../core/Exception.hpp" +#include "../network/network.h" #include "IniReader.h" extern "C" @@ -59,6 +60,68 @@ namespace Config } } + static void ReadNetwork(IIniReader * reader) + { + if (reader->ReadSection("network")) + { + auto model = &gConfigNetwork; + model->player_name = reader->GetCString("player_name", "Player"); + model->default_port = reader->GetSint32("default_port", NETWORK_DEFAULT_PORT); + model->default_password = reader->GetCString("default_password", nullptr); + model->stay_connected = reader->GetBoolean("stay_connected", true); + model->advertise = reader->GetBoolean("advertise", true); + model->maxplayers = reader->GetSint32("maxplayers", 16); + model->server_name = reader->GetCString("server_name", "Server"); + model->server_description = reader->GetCString("server_description", nullptr); + model->server_greeting = reader->GetCString("server_greeting", nullptr); + model->master_server_url = reader->GetCString("master_server_url", nullptr); + model->provider_name = reader->GetCString("provider_name", nullptr); + model->provider_email = reader->GetCString("provider_email", nullptr); + model->provider_website = reader->GetCString("provider_website", nullptr); + model->known_keys_only = reader->GetBoolean("known_keys_only", false); + model->log_chat = reader->GetBoolean("log_chat", false); + } + } + + static void ReadNotifications(IIniReader * reader) + { + if (reader->ReadSection("notifications")) + { + auto model = &gConfigNotifications; + model->park_award = reader->GetBoolean("park_award", true); + model->park_marketing_campaign_finished = reader->GetBoolean("park_marketing_campaign_finished", true); + model->park_warnings = reader->GetBoolean("park_warnings", true); + model->park_rating_warnings = reader->GetBoolean("park_rating_warnings", true); + model->ride_broken_down = reader->GetBoolean("ride_broken_down", true); + model->ride_crashed = reader->GetBoolean("ride_crashed", true); + model->ride_warnings = reader->GetBoolean("ride_warnings", true); + model->ride_researched = reader->GetBoolean("ride_researched", true); + model->guest_warnings = reader->GetBoolean("guest_warnings", true); + model->guest_lost = reader->GetBoolean("guest_lost", false); + model->guest_left_park = reader->GetBoolean("guest_entered_left_park", true); + model->guest_queuing_for_ride = reader->GetBoolean("guest_queuing_for_ride", true); + model->guest_on_ride = reader->GetBoolean("guest_on_ride", true); + model->guest_left_ride = reader->GetBoolean("guest_left_ride", true); + model->guest_bought_item = reader->GetBoolean("guest_bought_item", true); + model->guest_used_facility = reader->GetBoolean("guest_used_facility", true); + model->guest_died = reader->GetBoolean("guest_died", true); + } + } + + static void ReadTwitch(IIniReader * reader) + { + if (reader->ReadSection("sound")) + { + auto model = &gConfigTwitch; + model->channel = reader->GetCString("channel", nullptr); + model->enable_follower_peep_names = reader->GetBoolean("follower_peep_names", true); + model->enable_follower_peep_tracking = reader->GetBoolean("follower_peep_tracking", false); + model->enable_chat_peep_names = reader->GetBoolean("chat_peep_names", true); + model->enable_chat_peep_tracking = reader->GetBoolean("chat_peep_tracking", true); + model->enable_news = reader->GetBoolean("news", false); + } + } + static bool ReadFile(const std::string &path) { try @@ -66,6 +129,9 @@ namespace Config auto reader = std::unique_ptr(CreateIniReader(path)); ReadGeneral(reader.get()); ReadSound(reader.get()); + ReadNetwork(reader.get()); + ReadNotifications(reader.get()); + ReadTwitch(reader.get()); return true; } catch (const Exception &) From d8fae61e0cdc18069568e111f5acf588672df491 Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 15 Feb 2017 23:37:28 +0000 Subject: [PATCH 07/50] Add remaining config reading --- src/openrct2/config/Config.cpp | 180 ++++++++++++++++++++++++++++-- src/openrct2/config/IniReader.cpp | 12 ++ src/openrct2/config/IniReader.h | 1 + 3 files changed, 185 insertions(+), 8 deletions(-) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 77a3676dab..53f5ecec55 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -16,6 +16,8 @@ #include #include "../core/Exception.hpp" +#include "../interface/window.h" +#include "../localisation/language.h" #include "../network/network.h" #include "IniReader.h" @@ -26,21 +28,161 @@ extern "C" namespace Config { - static auto Enum_MeasurementFormat = ConfigEnum( + static auto Enum_MeasurementFormat = ConfigEnum( + { + ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), + ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), + ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), + }); + + static auto Enum_Currency = ConfigEnum( + { + ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), + ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), + ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), + ConfigEnumEntry("GBP", CURRENCY_POUNDS), + ConfigEnumEntry("USD", CURRENCY_DOLLARS), + ConfigEnumEntry("FRF", CURRENCY_FRANC), + ConfigEnumEntry("DEM", CURRENCY_DEUTSCHMARK), + ConfigEnumEntry("JPY", CURRENCY_YEN), + ConfigEnumEntry("ESP", CURRENCY_PESETA), + ConfigEnumEntry("ITL", CURRENCY_LIRA), + ConfigEnumEntry("NLG", CURRENCY_GUILDERS), + ConfigEnumEntry("SEK", CURRENCY_KRONA), + ConfigEnumEntry("EUR", CURRENCY_EUROS), + ConfigEnumEntry("KRW", CURRENCY_WON), + ConfigEnumEntry("RUB", CURRENCY_ROUBLE), + ConfigEnumEntry("CZK", CURRENCY_CZECH_KORUNA), + ConfigEnumEntry("HKD", CURRENCY_HKD), + ConfigEnumEntry("TWD", CURRENCY_TWD), + ConfigEnumEntry("CNY", CURRENCY_YUAN), + }); + + static auto Enum_CurrencySymbolAffix = ConfigEnum( + { + ConfigEnumEntry("PREFIX", CURRENCY_PREFIX), + ConfigEnumEntry("SUFFIX", CURRENCY_SUFFIX), + }); + + static auto Enum_CurrencySymbolAffix = ConfigEnum( + { + ConfigEnumEntry("PREFIX", CURRENCY_PREFIX), + ConfigEnumEntry("SUFFIX", CURRENCY_SUFFIX), + }); + + static auto Enum_DateFormat = ConfigEnum( + { + ConfigEnumEntry("DD/MM/YY", DATE_FORMAT_DMY), + ConfigEnumEntry("MM/DD/YY", DATE_FORMAT_MDY), + ConfigEnumEntry("YY/MM/DD", DATE_FORMAT_YMD), + ConfigEnumEntry("YY/DD/MM", DATE_FORMAT_YDM), + }); + + static auto Enum_DrawingEngine = ConfigEnum( + { + ConfigEnumEntry("SOFTWARE", DRAWING_ENGINE_SOFTWARE), + ConfigEnumEntry("SOFTWARE_HWD", DRAWING_ENGINE_SOFTWARE_WITH_HARDWARE_DISPLAY), + ConfigEnumEntry("OPENGL", DRAWING_ENGINE_OPENGL), + }); + + static auto Enum_Temperature = ConfigEnum( + { + ConfigEnumEntry("CELSIUS", TEMPERATURE_FORMAT_C), + ConfigEnumEntry("FAHRENHEIT", TEMPERATURE_FORMAT_F), + }); + + static auto Enum_LanguageEnum = ConfigEnum( { - ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), - ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), - ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), }); static void ReadGeneral(IIniReader * reader) { if (reader->ReadSection("general")) { - gConfigGeneral.always_show_gridlines = reader->GetBoolean("always_show_gridlines", false); - gConfigGeneral.window_width = reader->GetSint32("window_width", -1); - gConfigGeneral.window_height = reader->GetSint32("window_height", -1); - gConfigGeneral.measurement_format = reader->GetEnum("measurement_format", MEASUREMENT_FORMAT_METRIC, Enum_MeasurementFormat); + auto model = &gConfigGeneral; + model->always_show_gridlines = reader->GetBoolean("always_show_gridlines", false); + model->autosave_frequency = reader->GetSint32("autosave", AUTOSAVE_EVERY_5MINUTES); + model->confirmation_prompt = reader->GetBoolean("confirmation_prompt", false); + model->construction_marker_colour = reader->GetBoolean("construction_marker_colour", false); + model->currency_format = reader->GetEnum("currency_format", CURRENCY_POUNDS, Enum_Currency); + model->custom_currency_rate = reader->GetSint32("custom_currency_rate", 10); + model->custom_currency_affix = reader->GetEnum("custom_currency_affix", CURRENCY_SUFFIX, Enum_CurrencySymbolAffix); + model->custom_currency_symbol = reader->GetCString("custom_currency_symbol", "Ctm"); + model->edge_scrolling = reader->GetBoolean("edge_scrolling", true); + model->fullscreen_mode = reader->GetSint32("fullscreen_mode", 0); + model->fullscreen_height = reader->GetSint32("fullscreen_height", -1); + model->fullscreen_width = reader->GetSint32("fullscreen_width", -1); + model->rct1_path = reader->GetCString("rct1_path", nullptr); + model->rct2_path = reader->GetCString("game_path", nullptr); + model->landscape_smoothing = reader->GetBoolean("landscape_smoothing", true); + model->language = reader->GetEnum("language", LANGUAGE_ENGLISH_UK, Enum_LanguageEnum); + model->measurement_format = reader->GetEnum("measurement_format", MEASUREMENT_FORMAT_METRIC, Enum_MeasurementFormat); + model->play_intro = reader->GetBoolean("play_intro", false); + model->save_plugin_data = reader->GetBoolean("save_plugin_data", true); + model->debugging_tools = reader->GetBoolean("debugging_tools", false); + model->show_height_as_units = reader->GetBoolean("show_height_as_units", false); + model->temperature_format = reader->GetEnum("temperature_format", TEMPERATURE_FORMAT_C, Enum_Temperature); + model->window_height = reader->GetSint32("window_height", -1); + model->window_snap_proximity = reader->GetSint32("window_snap_proximity", 5); + model->window_width = reader->GetSint32("window_width", -1); + model->drawing_engine = reader->GetEnum("drawing_engine", DRAWING_ENGINE_SOFTWARE, Enum_DrawingEngine); + model->uncap_fps = reader->GetBoolean("uncap_fps", false); + + // Default config setting is false until ghost trains are implemented #4540 + model->test_unfinished_tracks = reader->GetBoolean("test_unfinished_tracks", false); + + model->no_test_crashes = reader->GetBoolean("no_test_crashes", false); + model->date_format = reader->GetEnum("date_format", DATE_FORMAT_DMY, Enum_DateFormat); + model->auto_staff_placement = reader->GetBoolean("auto_staff", true); + model->handymen_mow_default = reader->GetBoolean("handymen_mow_default", false); + model->default_inspection_interval = reader->GetSint32("default_inspection_interval", 2); + model->last_run_version = reader->GetCString("last_run_version", nullptr); + model->invert_viewport_drag = reader->GetBoolean("invert_viewport_drag", false); + model->load_save_sort = reader->GetSint32("load_save_sort", SORT_NAME_ASCENDING); + model->minimize_fullscreen_focus_loss = reader->GetBoolean("minimize_fullscreen_focus_loss", true); + + //Default config setting is false until the games canvas can be seperated from the effect + model->day_night_cycle = reader->GetBoolean("day_night_cycle", false); + + model->enable_light_fx = reader->GetBoolean("enable_light_fx", false); + model->upper_case_banners = reader->GetBoolean("upper_case_banners", false); + model->disable_lightning_effect = reader->GetBoolean("disable_lightning_effect", false); + model->allow_loading_with_incorrect_checksum = reader->GetBoolean("allow_loading_with_incorrect_checksum", true); + model->steam_overlay_pause = reader->GetBoolean("steam_overlay_pause", true); + model->window_scale = reader->GetFloat("window_scale", 1.0f); + model->scale_quality = reader->GetSint32("scale_quality", 1); + model->use_nn_at_integer_scales = reader->GetBoolean("use_nn_at_integer_scales", true); + model->show_fps = reader->GetBoolean("show_fps", false); + model->trap_cursor = reader->GetBoolean("trap_cursor", false); + model->auto_open_shops = reader->GetBoolean("auto_open_shops", false); + model->scenario_select_mode = reader->GetSint32("scenario_select_mode", SCENARIO_SELECT_MODE_ORIGIN); + model->scenario_unlocking_enabled = reader->GetBoolean("scenario_unlocking_enabled", true); + model->scenario_hide_mega_park = reader->GetBoolean("scenario_hide_mega_park", true); + model->last_save_game_directory = reader->GetCString("last_game_directory", nullptr); + model->last_save_landscape_directory = reader->GetCString("last_landscape_directory", nullptr); + model->last_save_scenario_directory = reader->GetCString("last_scenario_directory", nullptr); + model->last_save_track_directory = reader->GetCString("last_track_directory", nullptr); + model->window_limit = reader->GetBoolean("window_limit", WINDOW_LIMIT_MAX); + model->zoom_to_cursor = reader->GetBoolean("zoom_to_cursor", true); + model->render_weather_effects = reader->GetBoolean("render_weather_effects", true); + model->render_weather_gloom = reader->GetBoolean("render_weather_gloom", true); + } + } + + static void ReadInterface(IIniReader * reader) + { + if (reader->ReadSection("interface")) + { + auto model = &gConfigInterface; + model->toolbar_show_finances = reader->GetBoolean("toolbar_show_finances", true); + model->toolbar_show_research = reader->GetBoolean("toolbar_show_research", true); + model->toolbar_show_cheats = reader->GetBoolean("toolbar_show_cheats", false); + model->toolbar_show_news = reader->GetBoolean("toolbar_show_news", false); + model->select_by_track_type = reader->GetBoolean("select_by_track_type", false); + model->console_small_font = reader->GetBoolean("console_small_font", false); + model->current_theme_preset = reader->GetCString("current_theme", "*RCT2"); + model->current_title_sequence_preset = reader->GetCString("current_title_sequence", "*OPENRCT2"); + model->object_selection_filter_flags = reader->GetSint32("object_selection_filter_flags", 0x7EF); } } @@ -122,16 +264,38 @@ namespace Config } } + static void ReadFont(IIniReader * reader) + { + if (reader->ReadSection("font")) + { + auto model = &gConfigFonts; + model->file_name = reader->GetCString("file_name", nullptr); + model->font_name = reader->GetCString("font_name", nullptr); + model->x_offset = reader->GetSint32("x_offset", false); + model->y_offset = reader->GetSint32("y_offset", true); + model->size_tiny = reader->GetSint32("size_tiny", true); + model->size_small = reader->GetSint32("size_small", false); + model->size_medium = reader->GetSint32("size_medium", false); + model->size_big = reader->GetSint32("size_big", false); + model->height_tiny = reader->GetSint32("height_tiny", false); + model->height_small = reader->GetSint32("height_small", false); + model->height_medium = reader->GetSint32("height_medium", false); + model->height_big = reader->GetSint32("height_big", false); + } + } + static bool ReadFile(const std::string &path) { try { auto reader = std::unique_ptr(CreateIniReader(path)); ReadGeneral(reader.get()); + ReadInterface(reader.get()); ReadSound(reader.get()); ReadNetwork(reader.get()); ReadNotifications(reader.get()); ReadTwitch(reader.get()); + ReadFont(reader.get()); return true; } catch (const Exception &) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index a04a1b7fd5..dc6b1cec1d 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -116,6 +116,18 @@ public: return std::stoi(value); } + float GetFloat(const std::string &name, float defaultValue) const override + { + auto it = _values.find(name); + if (it == _values.end()) + { + return defaultValue; + } + + std::string value = it->second; + return std::stof(value); + } + std::string GetString(const std::string &name, const std::string &defaultValue) const override { auto it = _values.find(name); diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.h index 85dfc1b31d..5dcd2e7fca 100644 --- a/src/openrct2/config/IniReader.h +++ b/src/openrct2/config/IniReader.h @@ -26,6 +26,7 @@ interface IIniReader virtual bool GetBoolean(const std::string &name, bool defaultValue) const abstract; virtual sint32 GetSint32(const std::string &name, sint32 defaultValue) const abstract; + virtual float GetFloat(const std::string &name, float defaultValue) const abstract; virtual std::string GetString(const std::string &name, const std::string &defaultValue) const abstract; virtual bool TryGetString(const std::string &name, std::string * outValue) const abstract; From 0542338d4de0c4f6cfc0bb0e33f6ee55edf6d53a Mon Sep 17 00:00:00 2001 From: Ted John Date: Thu, 16 Feb 2017 00:03:02 +0000 Subject: [PATCH 08/50] Use interface for config enum --- src/openrct2/config.c | 2 +- src/openrct2/config/Config.cpp | 40 ++++++++++++++++++++++++-------- src/openrct2/config/ConfigEnum.h | 18 ++++++++++---- src/openrct2/config/IniReader.h | 2 +- 4 files changed, 45 insertions(+), 17 deletions(-) diff --git a/src/openrct2/config.c b/src/openrct2/config.c index 3368fe5cb0..4452ca17e8 100644 --- a/src/openrct2/config.c +++ b/src/openrct2/config.c @@ -500,7 +500,7 @@ bool config_save_default() return false; } -bool config_open_2(const utf8string path) +static bool config_open_2(const utf8string path) { SDL_RWops *file; utf8string lineBuffer; diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 53f5ecec55..a0b43dfb30 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -17,17 +17,19 @@ #include #include "../core/Exception.hpp" #include "../interface/window.h" -#include "../localisation/language.h" #include "../network/network.h" #include "IniReader.h" extern "C" { #include "../config.h" + #include "../localisation/language.h" } namespace Config { + #pragma region Enums + static auto Enum_MeasurementFormat = ConfigEnum( { ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), @@ -64,12 +66,6 @@ namespace Config ConfigEnumEntry("SUFFIX", CURRENCY_SUFFIX), }); - static auto Enum_CurrencySymbolAffix = ConfigEnum( - { - ConfigEnumEntry("PREFIX", CURRENCY_PREFIX), - ConfigEnumEntry("SUFFIX", CURRENCY_SUFFIX), - }); - static auto Enum_DateFormat = ConfigEnum( { ConfigEnumEntry("DD/MM/YY", DATE_FORMAT_DMY), @@ -91,9 +87,33 @@ namespace Config ConfigEnumEntry("FAHRENHEIT", TEMPERATURE_FORMAT_F), }); - static auto Enum_LanguageEnum = ConfigEnum( + /** + * Config enum wrapping LanguagesDescriptors. + */ + static class LanguageConfigEnum final : public IConfigEnum { - }); + public: + std::string GetName(sint32 value) const override + { + return LanguagesDescriptors[value].locale; + } + + sint32 GetValue(const std::string &key, sint32 defaultValue) const override + { + sint32 i = 0; + for (const auto &langDesc : LanguagesDescriptors) + { + if (String::Equals(key.c_str(), langDesc.locale)) + { + return i; + } + i++; + } + return defaultValue; + } + } Enum_LanguageEnum; + + #pragma endregion static void ReadGeneral(IIniReader * reader) { @@ -162,7 +182,7 @@ namespace Config model->last_save_landscape_directory = reader->GetCString("last_landscape_directory", nullptr); model->last_save_scenario_directory = reader->GetCString("last_scenario_directory", nullptr); model->last_save_track_directory = reader->GetCString("last_track_directory", nullptr); - model->window_limit = reader->GetBoolean("window_limit", WINDOW_LIMIT_MAX); + model->window_limit = reader->GetSint32("window_limit", WINDOW_LIMIT_MAX); model->zoom_to_cursor = reader->GetBoolean("zoom_to_cursor", true); model->render_weather_effects = reader->GetBoolean("render_weather_effects", true); model->render_weather_gloom = reader->GetBoolean("render_weather_gloom", true); diff --git a/src/openrct2/config/ConfigEnum.h b/src/openrct2/config/ConfigEnum.h index ef2013c338..5cd0c231e0 100644 --- a/src/openrct2/config/ConfigEnum.h +++ b/src/openrct2/config/ConfigEnum.h @@ -21,7 +21,7 @@ #include "../core/String.hpp" template -struct ConfigEnumEntry +struct ConfigEnumEntry final { std::string Key; T Value; @@ -34,7 +34,15 @@ struct ConfigEnumEntry }; template -class ConfigEnum +interface IConfigEnum +{ + virtual ~IConfigEnum() = default; + virtual std::string GetName(T value) const abstract; + virtual T GetValue(const std::string &key, T defaultValue) const abstract; +}; + +template +class ConfigEnum final : public IConfigEnum { private: std::vector> _entries; @@ -45,9 +53,9 @@ public: _entries = entries; } - std::string GetName(T value) + std::string GetName(T value) const override { - for (const auto &entry : _entries) const + for (const auto &entry : _entries) { if (entry.Value == value) { @@ -57,7 +65,7 @@ public: return std::string(); } - T GetValue(const std::string &key, T defaultValue) const + T GetValue(const std::string &key, T defaultValue) const override { for (const auto &entry : _entries) { diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.h index 5dcd2e7fca..5df6e1dc7a 100644 --- a/src/openrct2/config/IniReader.h +++ b/src/openrct2/config/IniReader.h @@ -31,7 +31,7 @@ interface IIniReader virtual bool TryGetString(const std::string &name, std::string * outValue) const abstract; template - T GetEnum(const std::string &name, T defaultValue, const ConfigEnum &configEnum) const + T GetEnum(const std::string &name, T defaultValue, const IConfigEnum &configEnum) const { std::string szValue; if (!TryGetString(name, &szValue)) From 2fc5012670970e5979480e43ef81af6922d0b4cc Mon Sep 17 00:00:00 2001 From: Ted John Date: Thu, 16 Feb 2017 00:06:22 +0000 Subject: [PATCH 09/50] Fix build errors --- src/openrct2/config/Config.cpp | 1 + src/openrct2/config/Config.h | 7 +++++++ src/openrct2/config/IniReader.cpp | 2 +- 3 files changed, 9 insertions(+), 1 deletion(-) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index a0b43dfb30..cf7d1b6ecd 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -18,6 +18,7 @@ #include "../core/Exception.hpp" #include "../interface/window.h" #include "../network/network.h" +#include "Config.h" #include "IniReader.h" extern "C" diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index 1ea5ab7cc9..13057fa82f 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -15,3 +15,10 @@ #pragma endregion #pragma once + +#include "../common.h" + +extern "C" +{ + bool config_open(const utf8 * path); +} diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index dc6b1cec1d..300eae90b2 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -267,7 +267,7 @@ private: { inQuotes = 0; } - else if (c == '\'' || c == '"' && !escaped) + else if ((c == '\'' || c == '"') && !escaped) { inQuotes = c; } From 23fef54b14cce99341860f61cf55f983d10719db Mon Sep 17 00:00:00 2001 From: Ted John Date: Thu, 16 Feb 2017 19:12:30 +0000 Subject: [PATCH 10/50] Implement IniWriter --- src/openrct2/config.c | 4 +- src/openrct2/config/Config.cpp | 54 +++++++++++++++++ src/openrct2/config/Config.h | 1 + src/openrct2/config/IniWriter.cpp | 96 +++++++++++++++++++++++++++++++ src/openrct2/config/IniWriter.h | 50 ++++++++++++++++ src/openrct2/libopenrct2.vcxproj | 2 + 6 files changed, 205 insertions(+), 2 deletions(-) create mode 100644 src/openrct2/config/IniWriter.cpp create mode 100644 src/openrct2/config/IniWriter.h diff --git a/src/openrct2/config.c b/src/openrct2/config.c index 4452ca17e8..2186bc470a 100644 --- a/src/openrct2/config.c +++ b/src/openrct2/config.c @@ -339,7 +339,7 @@ notification_configuration gConfigNotifications; font_configuration gConfigFonts; bool config_open(const utf8string path); -static bool config_save(const utf8string path); +bool config_save(const utf8string path); static void config_read_properties(config_section_definition **currentSection, const_utf8string line); static void config_save_property_value(SDL_RWops *file, uint8 type, value_union *value); static bool config_read_enum(void *dest, sint32 destSize, const utf8 *key, sint32 keySize, config_enum_definition *enumDefinitions); @@ -557,7 +557,7 @@ static bool config_open_2(const utf8string path) return true; } -bool config_save(const utf8string path) +static bool config_save_2(const utf8string path) { SDL_RWops *file; sint32 i, j; diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index cf7d1b6ecd..263eef6dfc 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -20,6 +20,7 @@ #include "../network/network.h" #include "Config.h" #include "IniReader.h" +#include "IniWriter.h" extern "C" { @@ -190,6 +191,10 @@ namespace Config } } + static void WriteGeneral(IIniWriter * writer) + { + } + static void ReadInterface(IIniReader * reader) { if (reader->ReadSection("interface")) @@ -207,6 +212,10 @@ namespace Config } } + static void WriteInterface(IIniWriter * writer) + { + } + static void ReadSound(IIniReader * reader) { if (reader->ReadSection("sound")) @@ -223,6 +232,10 @@ namespace Config } } + static void WriteSound(IIniWriter * writer) + { + } + static void ReadNetwork(IIniReader * reader) { if (reader->ReadSection("network")) @@ -246,6 +259,10 @@ namespace Config } } + static void WriteNetwork(IIniWriter * writer) + { + } + static void ReadNotifications(IIniReader * reader) { if (reader->ReadSection("notifications")) @@ -271,6 +288,10 @@ namespace Config } } + static void WriteNotifications(IIniWriter * writer) + { + } + static void ReadTwitch(IIniReader * reader) { if (reader->ReadSection("sound")) @@ -285,6 +306,10 @@ namespace Config } } + static void WriteTwitch(IIniWriter * writer) + { + } + static void ReadFont(IIniReader * reader) { if (reader->ReadSection("font")) @@ -305,6 +330,10 @@ namespace Config } } + static void WriteFont(IIniWriter * writer) + { + } + static bool ReadFile(const std::string &path) { try @@ -324,6 +353,26 @@ namespace Config return false; } } + + static bool WriteFile(const std::string &path) + { + try + { + auto writer = std::unique_ptr(CreateIniWriter(path)); + WriteGeneral(writer.get()); + WriteInterface(writer.get()); + WriteSound(writer.get()); + WriteNetwork(writer.get()); + WriteNotifications(writer.get()); + WriteTwitch(writer.get()); + WriteFont(writer.get()); + return true; + } + catch (const Exception &) + { + return false; + } + } } extern "C" @@ -332,4 +381,9 @@ extern "C" { return Config::ReadFile(path); } + + bool config_save(const utf8 * path) + { + return Config::WriteFile(path); + } } diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index 13057fa82f..5adf8efd3c 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -21,4 +21,5 @@ extern "C" { bool config_open(const utf8 * path); + bool config_save(const utf8 * path); } diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp new file mode 100644 index 0000000000..bfee401403 --- /dev/null +++ b/src/openrct2/config/IniWriter.cpp @@ -0,0 +1,96 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#include +#include "../core/FileStream.hpp" +#include "../platform/platform.h" +#include "IniWriter.h" + +class IniWriter final : public IIniWriter +{ +private: + FileStream _fs; + +public: + IniWriter(const std::string &path) + : _fs(path, FILE_MODE_WRITE) + { + } + + void WriteSection(const std::string &name) override + { + WriteLine("[" + name + "]"); + } + + void WriteBoolean(const std::string &name, bool value) + { + WriteProperty(name, value ? "true" : "false"); + } + + void WriteSint32(const std::string &name, sint32 value) override + { + WriteProperty(name, std::to_string(value)); + } + + void WriteFloat(const std::string &name, float value) override + { + WriteProperty(name, std::to_string(value)); + } + + void WriteString(const std::string &name, const std::string &value) override + { + std::ostringstream buffer; + buffer << '"'; + for (char c : value) + { + if (c == '\\' || c == '"') + { + buffer << '\\'; + } + buffer << c; + } + buffer << '"'; + + WriteProperty(name, buffer.str()); + } + + void WriteEnum(const std::string &name, const std::string &key) override + { + WriteProperty(name, key); + } + +private: + void WriteProperty(const std::string &name, const std::string &value) + { + WriteLine(name + " = " + value); + } + + void WriteLine(const std::string &line) + { + _fs.Write(line.c_str(), line.size()); + _fs.Write(PLATFORM_NEWLINE, String::SizeOf(PLATFORM_NEWLINE)); + } +}; + +void IIniWriter::WriteString(const std::string &name, const utf8 * value) +{ + WriteString(name, String::ToStd(value)); +} + +IIniWriter * CreateIniWriter(const std::string &path) +{ + return new IniWriter(path); +} diff --git a/src/openrct2/config/IniWriter.h b/src/openrct2/config/IniWriter.h new file mode 100644 index 0000000000..5aa6e82534 --- /dev/null +++ b/src/openrct2/config/IniWriter.h @@ -0,0 +1,50 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#include +#include "../common.h" +#include "ConfigEnum.h" + +interface IIniWriter +{ + virtual ~IIniWriter() = default; + + virtual void WriteSection(const std::string &name) abstract; + + virtual void WriteBoolean(const std::string &name, bool value) abstract; + virtual void WriteSint32(const std::string &name, sint32 value) abstract; + virtual void WriteFloat(const std::string &name, float value) abstract; + virtual void WriteString(const std::string &name, const std::string &value) abstract; + virtual void WriteEnum(const std::string &name, const std::string &key) abstract; + + template + void WriteEnum(const std::string &name, T value, const IConfigEnum &configEnum) + { + std::string key = configEnum.GetName(value); + if (key.empty) + { + WriteSint32(value); + } + else + { + WriteEnum(name, key); + } + } + + void WriteString(const std::string &name, const utf8 * value); +}; + +IIniWriter * CreateIniWriter(const std::string &path); diff --git a/src/openrct2/libopenrct2.vcxproj b/src/openrct2/libopenrct2.vcxproj index 2cb0e509af..689c958415 100644 --- a/src/openrct2/libopenrct2.vcxproj +++ b/src/openrct2/libopenrct2.vcxproj @@ -74,6 +74,7 @@ + @@ -424,6 +425,7 @@ + From bd6d31fed6515101bec70e58be98e14f2ecf7a09 Mon Sep 17 00:00:00 2001 From: Ted John Date: Thu, 16 Feb 2017 23:22:26 +0000 Subject: [PATCH 11/50] Write config fields --- src/openrct2/config/Config.cpp | 146 +++++++++++++++++++++++++++++++- src/openrct2/config/IniWriter.h | 4 +- 2 files changed, 147 insertions(+), 3 deletions(-) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 263eef6dfc..1e13c9946a 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -15,6 +15,7 @@ #pragma endregion #include +#include "../core/Console.hpp" #include "../core/Exception.hpp" #include "../interface/window.h" #include "../network/network.h" @@ -193,6 +194,68 @@ namespace Config static void WriteGeneral(IIniWriter * writer) { + auto model = &gConfigGeneral; + writer->WriteSection("general"); + writer->WriteBoolean("always_show_gridlines", model->always_show_gridlines != 0); + writer->WriteSint32("autosave", model->autosave_frequency); + writer->WriteBoolean("confirmation_prompt", model->confirmation_prompt != 0); + writer->WriteBoolean("construction_marker_colour", model->construction_marker_colour != 0); + writer->WriteEnum("currency_format", model->currency_format, Enum_Currency); + writer->WriteSint32("custom_currency_rate", model->custom_currency_rate != 0); + writer->WriteEnum("custom_currency_affix", model->custom_currency_affix, Enum_CurrencySymbolAffix); + writer->WriteString("custom_currency_symbol", model->custom_currency_symbol); + writer->WriteBoolean("edge_scrolling", model->edge_scrolling != 0); + writer->WriteSint32("fullscreen_mode", model->fullscreen_mode); + writer->WriteSint32("fullscreen_height", model->fullscreen_height); + writer->WriteSint32("fullscreen_width", model->fullscreen_width); + writer->WriteString("rct1_path", model->rct1_path); + writer->WriteString("game_path", model->rct2_path); + writer->WriteBoolean("landscape_smoothing", model->landscape_smoothing != 0); + writer->WriteEnum("language", model->language, Enum_LanguageEnum); + writer->WriteEnum("measurement_format", model->measurement_format, Enum_MeasurementFormat); + writer->WriteBoolean("play_intro", model->play_intro != 0); + writer->WriteBoolean("save_plugin_data", model->save_plugin_data != 0); + writer->WriteBoolean("debugging_tools", model->debugging_tools != 0); + writer->WriteBoolean("show_height_as_units", model->show_height_as_units != 0); + writer->WriteEnum("temperature_format", model->temperature_format, Enum_Temperature); + writer->WriteSint32("window_height", model->window_height); + writer->WriteSint32("window_snap_proximity", model->window_snap_proximity); + writer->WriteSint32("window_width", model->window_width); + writer->WriteEnum("drawing_engine", model->drawing_engine, Enum_DrawingEngine); + writer->WriteBoolean("uncap_fps", model->uncap_fps != 0); + writer->WriteBoolean("test_unfinished_tracks", model->test_unfinished_tracks != 0); + writer->WriteBoolean("no_test_crashes", model->no_test_crashes != 0); + writer->WriteEnum("date_format", model->date_format, Enum_DateFormat); + writer->WriteBoolean("auto_staff", model->auto_staff_placement != 0); + writer->WriteBoolean("handymen_mow_default", model->handymen_mow_default != 0); + writer->WriteSint32("default_inspection_interval", model->default_inspection_interval); + writer->WriteString("last_run_version", model->last_run_version); + writer->WriteBoolean("invert_viewport_drag", model->invert_viewport_drag != 0); + writer->WriteSint32("load_save_sort", model->load_save_sort); + writer->WriteBoolean("minimize_fullscreen_focus_loss", model->minimize_fullscreen_focus_loss != 0); + writer->WriteBoolean("day_night_cycle", model->day_night_cycle != 0); + writer->WriteBoolean("enable_light_fx", model->enable_light_fx != 0); + writer->WriteBoolean("upper_case_banners", model->upper_case_banners != 0); + writer->WriteBoolean("disable_lightning_effect", model->disable_lightning_effect != 0); + writer->WriteBoolean("allow_loading_with_incorrect_checksum", model->allow_loading_with_incorrect_checksum != 0); + writer->WriteBoolean("steam_overlay_pause", model->steam_overlay_pause != 0); + writer->WriteFloat("window_scale", model->window_scale); + writer->WriteSint32("scale_quality", model->scale_quality); + writer->WriteBoolean("use_nn_at_integer_scales", model->use_nn_at_integer_scales != 0); + writer->WriteBoolean("show_fps", model->show_fps != 0); + writer->WriteBoolean("trap_cursor", model->trap_cursor != 0); + writer->WriteBoolean("auto_open_shops", model->auto_open_shops != 0); + writer->WriteSint32("scenario_select_mode", model->scenario_select_mode); + writer->WriteBoolean("scenario_unlocking_enabled", model->scenario_unlocking_enabled != 0); + writer->WriteBoolean("scenario_hide_mega_park", model->scenario_hide_mega_park != 0); + writer->WriteString("last_game_directory", model->last_save_game_directory); + writer->WriteString("last_landscape_directory", model->last_save_landscape_directory); + writer->WriteString("last_scenario_directory", model->last_save_scenario_directory); + writer->WriteString("last_track_directory", model->last_save_track_directory); + writer->WriteSint32("window_limit", model->window_limit); + writer->WriteBoolean("zoom_to_cursor", model->zoom_to_cursor != 0); + writer->WriteBoolean("render_weather_effects", model->render_weather_effects != 0); + writer->WriteBoolean("render_weather_gloom", model->render_weather_gloom != 0); } static void ReadInterface(IIniReader * reader) @@ -214,6 +277,17 @@ namespace Config static void WriteInterface(IIniWriter * writer) { + auto model = &gConfigInterface; + writer->WriteSection("interface"); + writer->WriteBoolean("toolbar_show_finances", model->toolbar_show_finances != 0); + writer->WriteBoolean("toolbar_show_research", model->toolbar_show_research != 0); + writer->WriteBoolean("toolbar_show_cheats", model->toolbar_show_cheats != 0); + writer->WriteBoolean("toolbar_show_news", model->toolbar_show_news != 0); + writer->WriteBoolean("select_by_track_type", model->select_by_track_type != 0); + writer->WriteBoolean("console_small_font", model->console_small_font != 0); + writer->WriteString("current_theme", model->current_theme_preset); + writer->WriteString("current_title_sequence", model->current_title_sequence_preset); + writer->WriteSint32("object_selection_filter_flags", model->object_selection_filter_flags); } static void ReadSound(IIniReader * reader) @@ -234,6 +308,16 @@ namespace Config static void WriteSound(IIniWriter * writer) { + auto model = &gConfigSound; + writer->WriteSection("sound"); + writer->WriteSint32("master_volume", model->master_volume); + writer->WriteSint32("title_music", model->title_music); + writer->WriteBoolean("sound", model->sound_enabled != 0); + writer->WriteSint32("sound_volume", model->sound_volume); + writer->WriteBoolean("ride_music", model->ride_music_enabled != 0); + writer->WriteSint32("ride_music_volume", model->ride_music_volume); + writer->WriteBoolean("audio_focus", model->audio_focus != 0); + writer->WriteString("audio_device", model->device); } static void ReadNetwork(IIniReader * reader) @@ -261,6 +345,23 @@ namespace Config static void WriteNetwork(IIniWriter * writer) { + auto model = &gConfigNetwork; + writer->WriteSection("network"); + writer->WriteString("player_name", model->player_name); + writer->WriteSint32("default_port", model->default_port); + writer->WriteString("default_password", model->default_password); + writer->WriteBoolean("stay_connected", model->stay_connected != 0); + writer->WriteBoolean("advertise", model->advertise != 0); + writer->WriteSint32("maxplayers", model->maxplayers); + writer->WriteString("server_name", model->server_name); + writer->WriteString("server_description", model->server_description); + writer->WriteString("server_greeting", model->server_greeting); + writer->WriteString("master_server_url", model->master_server_url); + writer->WriteString("provider_name", model->provider_name); + writer->WriteString("provider_email", model->provider_email); + writer->WriteString("provider_website", model->provider_website); + writer->WriteBoolean("known_keys_only", model->known_keys_only != 0); + writer->WriteBoolean("log_chat", model->log_chat != 0); } static void ReadNotifications(IIniReader * reader) @@ -290,6 +391,25 @@ namespace Config static void WriteNotifications(IIniWriter * writer) { + auto model = &gConfigNotifications; + writer->WriteSection("notifications"); + writer->WriteBoolean("park_award", model->park_award != 0); + writer->WriteBoolean("park_marketing_campaign_finished", model->park_marketing_campaign_finished != 0); + writer->WriteBoolean("park_warnings", model->park_warnings != 0); + writer->WriteBoolean("park_rating_warnings", model->park_rating_warnings != 0); + writer->WriteBoolean("ride_broken_down", model->ride_broken_down != 0); + writer->WriteBoolean("ride_crashed", model->ride_crashed != 0); + writer->WriteBoolean("ride_warnings", model->ride_warnings != 0); + writer->WriteBoolean("ride_researched", model->ride_researched != 0); + writer->WriteBoolean("guest_warnings", model->guest_warnings != 0); + writer->WriteBoolean("guest_lost", model->guest_lost != 0); + writer->WriteBoolean("guest_left_park", model->guest_left_park != 0); + writer->WriteBoolean("guest_queuing_for_ride", model->guest_queuing_for_ride != 0); + writer->WriteBoolean("guest_on_ride", model->guest_on_ride != 0); + writer->WriteBoolean("guest_left_ride", model->guest_left_ride != 0); + writer->WriteBoolean("guest_bought_item", model->guest_bought_item != 0); + writer->WriteBoolean("guest_used_facility", model->guest_used_facility != 0); + writer->WriteBoolean("guest_died", model->guest_died != 0); } static void ReadTwitch(IIniReader * reader) @@ -308,6 +428,14 @@ namespace Config static void WriteTwitch(IIniWriter * writer) { + auto model = &gConfigTwitch; + writer->WriteSection("twitch"); + writer->WriteString("channel", model->channel); + writer->WriteBoolean("follower_peep_names", model->enable_follower_peep_names != 0); + writer->WriteBoolean("follower_peep_tracking", model->enable_follower_peep_tracking != 0); + writer->WriteBoolean("chat_peep_names", model->enable_chat_peep_names != 0); + writer->WriteBoolean("chat_peep_tracking", model->enable_chat_peep_tracking != 0); + writer->WriteBoolean("news", model->enable_news != 0); } static void ReadFont(IIniReader * reader) @@ -332,6 +460,20 @@ namespace Config static void WriteFont(IIniWriter * writer) { + auto model = &gConfigFonts; + writer->WriteSection("font"); + writer->WriteString("file_name", model->file_name); + writer->WriteString("font_name", model->font_name); + writer->WriteSint32("x_offset", model->x_offset); + writer->WriteSint32("y_offset", model->y_offset); + writer->WriteSint32("size_tiny", model->size_tiny); + writer->WriteSint32("size_small", model->size_small); + writer->WriteSint32("size_medium", model->size_medium); + writer->WriteSint32("size_big", model->size_big); + writer->WriteSint32("height_tiny", model->height_tiny); + writer->WriteSint32("height_small", model->height_small); + writer->WriteSint32("height_medium", model->height_medium); + writer->WriteSint32("height_big", model->height_big); } static bool ReadFile(const std::string &path) @@ -368,8 +510,10 @@ namespace Config WriteFont(writer.get()); return true; } - catch (const Exception &) + catch (const Exception &ex) { + Console::WriteLine("Error saving to '%s'", path.c_str()); + Console::WriteLine(ex.GetMessage()); return false; } } diff --git a/src/openrct2/config/IniWriter.h b/src/openrct2/config/IniWriter.h index 5aa6e82534..be409f32ed 100644 --- a/src/openrct2/config/IniWriter.h +++ b/src/openrct2/config/IniWriter.h @@ -34,9 +34,9 @@ interface IIniWriter void WriteEnum(const std::string &name, T value, const IConfigEnum &configEnum) { std::string key = configEnum.GetName(value); - if (key.empty) + if (key.empty()) { - WriteSint32(value); + WriteSint32(name, value); } else { From 6a2b7b1200b62bbf902e6a276a39c62b62344c53 Mon Sep 17 00:00:00 2001 From: Ted John Date: Sat, 18 Feb 2017 10:54:13 +0000 Subject: [PATCH 12/50] Start moving config definitions over to C++ --- src/openrct2/config.h | 221 ------------------------ src/openrct2/config/Config.cpp | 137 +++++++-------- src/openrct2/config/Config.h | 232 ++++++++++++++++++++++++++ src/openrct2/drawing/IDrawingEngine.h | 8 + 4 files changed, 309 insertions(+), 289 deletions(-) diff --git a/src/openrct2/config.h b/src/openrct2/config.h index c04568503e..5b161d5fb2 100644 --- a/src/openrct2/config.h +++ b/src/openrct2/config.h @@ -85,232 +85,11 @@ enum { SHORTCUT_COUNT }; -enum { - TEMPERATURE_FORMAT_C, - TEMPERATURE_FORMAT_F -}; - -enum { - MEASUREMENT_FORMAT_IMPERIAL, - MEASUREMENT_FORMAT_METRIC, - MEASUREMENT_FORMAT_SI -}; - -enum { - AUTOSAVE_EVERY_MINUTE, - AUTOSAVE_EVERY_5MINUTES, - AUTOSAVE_EVERY_15MINUTES, - AUTOSAVE_EVERY_30MINUTES, - AUTOSAVE_EVERY_HOUR, - AUTOSAVE_NEVER -}; - -enum { - DATE_FORMAT_DMY, - DATE_FORMAT_MDY, - DATE_FORMAT_YMD, - DATE_FORMAT_YDM -}; - -enum { - TITLE_SEQUENCE_RCT1, - TITLE_SEQUENCE_RCT1_AA, - TITLE_SEQUENCE_RCT1_AA_LL, - TITLE_SEQUENCE_RCT2, - TITLE_SEQUENCE_OPENRCT2, - TITLE_SEQUENCE_RANDOM -}; - -enum { - SORT_NAME_ASCENDING, - SORT_NAME_DESCENDING, - SORT_DATE_ASCENDING, - SORT_DATE_DESCENDING, -}; - -enum { - SCENARIO_SELECT_MODE_DIFFICULTY, - SCENARIO_SELECT_MODE_ORIGIN, -}; - -enum { - DRAWING_ENGINE_NONE = -1, - DRAWING_ENGINE_SOFTWARE, - DRAWING_ENGINE_SOFTWARE_WITH_HARDWARE_DISPLAY, - DRAWING_ENGINE_OPENGL, -}; - -typedef struct general_configuration { - uint8 play_intro; - uint8 confirmation_prompt; - uint8 screenshot_format; - utf8string rct1_path; - utf8string rct2_path; - sint8 measurement_format; - sint8 temperature_format; - sint8 currency_format; - sint32 custom_currency_rate; - sint8 custom_currency_affix; - utf8string custom_currency_symbol; - sint8 construction_marker_colour; - sint8 edge_scrolling; - sint8 always_show_gridlines; - sint8 landscape_smoothing; - sint8 show_height_as_units; - sint8 save_plugin_data; - uint8 debugging_tools; - - //new - uint8 fullscreen_mode; - sint32 fullscreen_width; - sint32 fullscreen_height; - sint32 window_width; - sint32 window_height; - uint16 language; - uint8 window_snap_proximity; - uint8 autosave_frequency; - uint8 drawing_engine; - uint8 uncap_fps; - uint8 test_unfinished_tracks; - uint8 no_test_crashes; - uint8 date_format; - uint8 auto_staff_placement; - uint8 handymen_mow_default; - uint8 default_inspection_interval; - utf8string last_run_version; - uint8 invert_viewport_drag; - uint8 load_save_sort; - uint8 minimize_fullscreen_focus_loss; - uint8 day_night_cycle; - uint8 enable_light_fx; - uint8 upper_case_banners; - uint8 disable_lightning_effect; - uint8 allow_loading_with_incorrect_checksum; - uint8 steam_overlay_pause; - float window_scale; - uint8 scale_quality; - uint8 use_nn_at_integer_scales; - uint8 show_fps; - uint8 trap_cursor; - uint8 auto_open_shops; - uint8 scenario_select_mode; - uint8 scenario_unlocking_enabled; - uint8 scenario_hide_mega_park; - utf8string last_save_game_directory; - utf8string last_save_landscape_directory; - utf8string last_save_scenario_directory; - utf8string last_save_track_directory; - uint8 window_limit; - uint8 zoom_to_cursor; - uint8 render_weather_effects; - uint8 render_weather_gloom; -} general_configuration; - -typedef struct interface_configuration { - uint8 toolbar_show_finances; - uint8 toolbar_show_research; - uint8 toolbar_show_cheats; - uint8 toolbar_show_news; - uint8 select_by_track_type; - uint8 console_small_font; - utf8string current_theme_preset; - utf8string current_title_sequence_preset; - uint32 object_selection_filter_flags; -} interface_configuration; - -typedef struct sound_configuration { - uint8 master_volume; - uint8 title_music; - uint8 sound_enabled; - uint8 sound_volume; - uint8 ride_music_enabled; - uint8 ride_music_volume; - uint8 audio_focus; - utf8string device; -} sound_configuration; - -typedef struct twitch_configuration { - utf8string channel; - uint8 enable_follower_peep_names; - uint8 enable_follower_peep_tracking; - uint8 enable_chat_peep_names; - uint8 enable_chat_peep_tracking; - uint8 enable_news; -} twitch_configuration; - -typedef struct network_configuration { - utf8string player_name; - uint32 default_port; - utf8string default_password; - uint8 stay_connected; - uint8 advertise; - uint8 maxplayers; - utf8string server_name; - utf8string server_description; - utf8string server_greeting; - utf8string master_server_url; - utf8string provider_name; - utf8string provider_email; - utf8string provider_website; - uint8 known_keys_only; - uint8 log_chat; -} network_configuration; - -typedef struct notification_configuration { - bool park_award; - bool park_marketing_campaign_finished; - bool park_warnings; - bool park_rating_warnings; - bool ride_broken_down; - bool ride_crashed; - bool ride_warnings; - bool ride_researched; - bool guest_warnings; - bool guest_lost; - bool guest_left_park; - bool guest_queuing_for_ride; - bool guest_on_ride; - bool guest_left_ride; - bool guest_bought_item; - bool guest_used_facility; - bool guest_died; -} notification_configuration; - -typedef struct font_configuration { - utf8string file_name; - utf8string font_name; - sint8 x_offset; - sint8 y_offset; - uint8 size_tiny; - uint8 size_small; - uint8 size_medium; - uint8 size_big; - uint8 height_tiny; - uint8 height_small; - uint8 height_medium; - uint8 height_big; -} font_configuration; - -// Define structures for any other settings here -typedef struct theme_features { - uint8 rct1_ride_lights; - uint8 rct1_park_lights; - uint8 rct1_scenario_font; -} theme_features; - typedef struct shortcut_entry { uint8 key; uint8 modifier; } shortcut_entry; -extern general_configuration gConfigGeneral; -extern interface_configuration gConfigInterface; -extern sound_configuration gConfigSound; -extern twitch_configuration gConfigTwitch; -extern network_configuration gConfigNetwork; -extern notification_configuration gConfigNotifications; -extern font_configuration gConfigFonts; - extern uint16 gShortcutKeys[SHORTCUT_COUNT]; void config_get_default_path(utf8 *outPath, size_t size); diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 1e13c9946a..f3ed840f3a 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -17,6 +17,7 @@ #include #include "../core/Console.hpp" #include "../core/Exception.hpp" +#include "../drawing/IDrawingEngine.h" #include "../interface/window.h" #include "../network/network.h" #include "Config.h" @@ -25,7 +26,7 @@ extern "C" { - #include "../config.h" + #include "../localisation/currency.h" #include "../localisation/language.h" } @@ -196,66 +197,66 @@ namespace Config { auto model = &gConfigGeneral; writer->WriteSection("general"); - writer->WriteBoolean("always_show_gridlines", model->always_show_gridlines != 0); + writer->WriteBoolean("always_show_gridlines", model->always_show_gridlines); writer->WriteSint32("autosave", model->autosave_frequency); - writer->WriteBoolean("confirmation_prompt", model->confirmation_prompt != 0); - writer->WriteBoolean("construction_marker_colour", model->construction_marker_colour != 0); + writer->WriteBoolean("confirmation_prompt", model->confirmation_prompt); + writer->WriteBoolean("construction_marker_colour", model->construction_marker_colour); writer->WriteEnum("currency_format", model->currency_format, Enum_Currency); - writer->WriteSint32("custom_currency_rate", model->custom_currency_rate != 0); + writer->WriteSint32("custom_currency_rate", model->custom_currency_rate); writer->WriteEnum("custom_currency_affix", model->custom_currency_affix, Enum_CurrencySymbolAffix); writer->WriteString("custom_currency_symbol", model->custom_currency_symbol); - writer->WriteBoolean("edge_scrolling", model->edge_scrolling != 0); + writer->WriteBoolean("edge_scrolling", model->edge_scrolling); writer->WriteSint32("fullscreen_mode", model->fullscreen_mode); writer->WriteSint32("fullscreen_height", model->fullscreen_height); writer->WriteSint32("fullscreen_width", model->fullscreen_width); writer->WriteString("rct1_path", model->rct1_path); writer->WriteString("game_path", model->rct2_path); - writer->WriteBoolean("landscape_smoothing", model->landscape_smoothing != 0); + writer->WriteBoolean("landscape_smoothing", model->landscape_smoothing); writer->WriteEnum("language", model->language, Enum_LanguageEnum); writer->WriteEnum("measurement_format", model->measurement_format, Enum_MeasurementFormat); - writer->WriteBoolean("play_intro", model->play_intro != 0); - writer->WriteBoolean("save_plugin_data", model->save_plugin_data != 0); - writer->WriteBoolean("debugging_tools", model->debugging_tools != 0); - writer->WriteBoolean("show_height_as_units", model->show_height_as_units != 0); + writer->WriteBoolean("play_intro", model->play_intro); + writer->WriteBoolean("save_plugin_data", model->save_plugin_data); + writer->WriteBoolean("debugging_tools", model->debugging_tools); + writer->WriteBoolean("show_height_as_units", model->show_height_as_units); writer->WriteEnum("temperature_format", model->temperature_format, Enum_Temperature); writer->WriteSint32("window_height", model->window_height); writer->WriteSint32("window_snap_proximity", model->window_snap_proximity); writer->WriteSint32("window_width", model->window_width); writer->WriteEnum("drawing_engine", model->drawing_engine, Enum_DrawingEngine); - writer->WriteBoolean("uncap_fps", model->uncap_fps != 0); - writer->WriteBoolean("test_unfinished_tracks", model->test_unfinished_tracks != 0); - writer->WriteBoolean("no_test_crashes", model->no_test_crashes != 0); + writer->WriteBoolean("uncap_fps", model->uncap_fps); + writer->WriteBoolean("test_unfinished_tracks", model->test_unfinished_tracks); + writer->WriteBoolean("no_test_crashes", model->no_test_crashes); writer->WriteEnum("date_format", model->date_format, Enum_DateFormat); - writer->WriteBoolean("auto_staff", model->auto_staff_placement != 0); - writer->WriteBoolean("handymen_mow_default", model->handymen_mow_default != 0); + writer->WriteBoolean("auto_staff", model->auto_staff_placement); + writer->WriteBoolean("handymen_mow_default", model->handymen_mow_default); writer->WriteSint32("default_inspection_interval", model->default_inspection_interval); writer->WriteString("last_run_version", model->last_run_version); - writer->WriteBoolean("invert_viewport_drag", model->invert_viewport_drag != 0); + writer->WriteBoolean("invert_viewport_drag", model->invert_viewport_drag); writer->WriteSint32("load_save_sort", model->load_save_sort); - writer->WriteBoolean("minimize_fullscreen_focus_loss", model->minimize_fullscreen_focus_loss != 0); - writer->WriteBoolean("day_night_cycle", model->day_night_cycle != 0); - writer->WriteBoolean("enable_light_fx", model->enable_light_fx != 0); - writer->WriteBoolean("upper_case_banners", model->upper_case_banners != 0); - writer->WriteBoolean("disable_lightning_effect", model->disable_lightning_effect != 0); - writer->WriteBoolean("allow_loading_with_incorrect_checksum", model->allow_loading_with_incorrect_checksum != 0); - writer->WriteBoolean("steam_overlay_pause", model->steam_overlay_pause != 0); + writer->WriteBoolean("minimize_fullscreen_focus_loss", model->minimize_fullscreen_focus_loss); + writer->WriteBoolean("day_night_cycle", model->day_night_cycle); + writer->WriteBoolean("enable_light_fx", model->enable_light_fx); + writer->WriteBoolean("upper_case_banners", model->upper_case_banners); + writer->WriteBoolean("disable_lightning_effect", model->disable_lightning_effect); + writer->WriteBoolean("allow_loading_with_incorrect_checksum", model->allow_loading_with_incorrect_checksum); + writer->WriteBoolean("steam_overlay_pause", model->steam_overlay_pause); writer->WriteFloat("window_scale", model->window_scale); writer->WriteSint32("scale_quality", model->scale_quality); - writer->WriteBoolean("use_nn_at_integer_scales", model->use_nn_at_integer_scales != 0); - writer->WriteBoolean("show_fps", model->show_fps != 0); - writer->WriteBoolean("trap_cursor", model->trap_cursor != 0); - writer->WriteBoolean("auto_open_shops", model->auto_open_shops != 0); + writer->WriteBoolean("use_nn_at_integer_scales", model->use_nn_at_integer_scales); + writer->WriteBoolean("show_fps", model->show_fps); + writer->WriteBoolean("trap_cursor", model->trap_cursor); + writer->WriteBoolean("auto_open_shops", model->auto_open_shops); writer->WriteSint32("scenario_select_mode", model->scenario_select_mode); - writer->WriteBoolean("scenario_unlocking_enabled", model->scenario_unlocking_enabled != 0); - writer->WriteBoolean("scenario_hide_mega_park", model->scenario_hide_mega_park != 0); + writer->WriteBoolean("scenario_unlocking_enabled", model->scenario_unlocking_enabled); + writer->WriteBoolean("scenario_hide_mega_park", model->scenario_hide_mega_park); writer->WriteString("last_game_directory", model->last_save_game_directory); writer->WriteString("last_landscape_directory", model->last_save_landscape_directory); writer->WriteString("last_scenario_directory", model->last_save_scenario_directory); writer->WriteString("last_track_directory", model->last_save_track_directory); writer->WriteSint32("window_limit", model->window_limit); - writer->WriteBoolean("zoom_to_cursor", model->zoom_to_cursor != 0); - writer->WriteBoolean("render_weather_effects", model->render_weather_effects != 0); - writer->WriteBoolean("render_weather_gloom", model->render_weather_gloom != 0); + writer->WriteBoolean("zoom_to_cursor", model->zoom_to_cursor); + writer->WriteBoolean("render_weather_effects", model->render_weather_effects); + writer->WriteBoolean("render_weather_gloom", model->render_weather_gloom); } static void ReadInterface(IIniReader * reader) @@ -279,12 +280,12 @@ namespace Config { auto model = &gConfigInterface; writer->WriteSection("interface"); - writer->WriteBoolean("toolbar_show_finances", model->toolbar_show_finances != 0); - writer->WriteBoolean("toolbar_show_research", model->toolbar_show_research != 0); - writer->WriteBoolean("toolbar_show_cheats", model->toolbar_show_cheats != 0); - writer->WriteBoolean("toolbar_show_news", model->toolbar_show_news != 0); - writer->WriteBoolean("select_by_track_type", model->select_by_track_type != 0); - writer->WriteBoolean("console_small_font", model->console_small_font != 0); + writer->WriteBoolean("toolbar_show_finances", model->toolbar_show_finances); + writer->WriteBoolean("toolbar_show_research", model->toolbar_show_research); + writer->WriteBoolean("toolbar_show_cheats", model->toolbar_show_cheats); + writer->WriteBoolean("toolbar_show_news", model->toolbar_show_news); + writer->WriteBoolean("select_by_track_type", model->select_by_track_type); + writer->WriteBoolean("console_small_font", model->console_small_font); writer->WriteString("current_theme", model->current_theme_preset); writer->WriteString("current_title_sequence", model->current_title_sequence_preset); writer->WriteSint32("object_selection_filter_flags", model->object_selection_filter_flags); @@ -312,11 +313,11 @@ namespace Config writer->WriteSection("sound"); writer->WriteSint32("master_volume", model->master_volume); writer->WriteSint32("title_music", model->title_music); - writer->WriteBoolean("sound", model->sound_enabled != 0); + writer->WriteBoolean("sound", model->sound_enabled); writer->WriteSint32("sound_volume", model->sound_volume); - writer->WriteBoolean("ride_music", model->ride_music_enabled != 0); + writer->WriteBoolean("ride_music", model->ride_music_enabled); writer->WriteSint32("ride_music_volume", model->ride_music_volume); - writer->WriteBoolean("audio_focus", model->audio_focus != 0); + writer->WriteBoolean("audio_focus", model->audio_focus); writer->WriteString("audio_device", model->device); } @@ -350,8 +351,8 @@ namespace Config writer->WriteString("player_name", model->player_name); writer->WriteSint32("default_port", model->default_port); writer->WriteString("default_password", model->default_password); - writer->WriteBoolean("stay_connected", model->stay_connected != 0); - writer->WriteBoolean("advertise", model->advertise != 0); + writer->WriteBoolean("stay_connected", model->stay_connected); + writer->WriteBoolean("advertise", model->advertise); writer->WriteSint32("maxplayers", model->maxplayers); writer->WriteString("server_name", model->server_name); writer->WriteString("server_description", model->server_description); @@ -360,8 +361,8 @@ namespace Config writer->WriteString("provider_name", model->provider_name); writer->WriteString("provider_email", model->provider_email); writer->WriteString("provider_website", model->provider_website); - writer->WriteBoolean("known_keys_only", model->known_keys_only != 0); - writer->WriteBoolean("log_chat", model->log_chat != 0); + writer->WriteBoolean("known_keys_only", model->known_keys_only); + writer->WriteBoolean("log_chat", model->log_chat); } static void ReadNotifications(IIniReader * reader) @@ -393,23 +394,23 @@ namespace Config { auto model = &gConfigNotifications; writer->WriteSection("notifications"); - writer->WriteBoolean("park_award", model->park_award != 0); - writer->WriteBoolean("park_marketing_campaign_finished", model->park_marketing_campaign_finished != 0); - writer->WriteBoolean("park_warnings", model->park_warnings != 0); - writer->WriteBoolean("park_rating_warnings", model->park_rating_warnings != 0); - writer->WriteBoolean("ride_broken_down", model->ride_broken_down != 0); - writer->WriteBoolean("ride_crashed", model->ride_crashed != 0); - writer->WriteBoolean("ride_warnings", model->ride_warnings != 0); - writer->WriteBoolean("ride_researched", model->ride_researched != 0); - writer->WriteBoolean("guest_warnings", model->guest_warnings != 0); - writer->WriteBoolean("guest_lost", model->guest_lost != 0); - writer->WriteBoolean("guest_left_park", model->guest_left_park != 0); - writer->WriteBoolean("guest_queuing_for_ride", model->guest_queuing_for_ride != 0); - writer->WriteBoolean("guest_on_ride", model->guest_on_ride != 0); - writer->WriteBoolean("guest_left_ride", model->guest_left_ride != 0); - writer->WriteBoolean("guest_bought_item", model->guest_bought_item != 0); - writer->WriteBoolean("guest_used_facility", model->guest_used_facility != 0); - writer->WriteBoolean("guest_died", model->guest_died != 0); + writer->WriteBoolean("park_award", model->park_award); + writer->WriteBoolean("park_marketing_campaign_finished", model->park_marketing_campaign_finished); + writer->WriteBoolean("park_warnings", model->park_warnings); + writer->WriteBoolean("park_rating_warnings", model->park_rating_warnings); + writer->WriteBoolean("ride_broken_down", model->ride_broken_down); + writer->WriteBoolean("ride_crashed", model->ride_crashed); + writer->WriteBoolean("ride_warnings", model->ride_warnings); + writer->WriteBoolean("ride_researched", model->ride_researched); + writer->WriteBoolean("guest_warnings", model->guest_warnings); + writer->WriteBoolean("guest_lost", model->guest_lost); + writer->WriteBoolean("guest_left_park", model->guest_left_park); + writer->WriteBoolean("guest_queuing_for_ride", model->guest_queuing_for_ride); + writer->WriteBoolean("guest_on_ride", model->guest_on_ride); + writer->WriteBoolean("guest_left_ride", model->guest_left_ride); + writer->WriteBoolean("guest_bought_item", model->guest_bought_item); + writer->WriteBoolean("guest_used_facility", model->guest_used_facility); + writer->WriteBoolean("guest_died", model->guest_died); } static void ReadTwitch(IIniReader * reader) @@ -431,11 +432,11 @@ namespace Config auto model = &gConfigTwitch; writer->WriteSection("twitch"); writer->WriteString("channel", model->channel); - writer->WriteBoolean("follower_peep_names", model->enable_follower_peep_names != 0); - writer->WriteBoolean("follower_peep_tracking", model->enable_follower_peep_tracking != 0); - writer->WriteBoolean("chat_peep_names", model->enable_chat_peep_names != 0); - writer->WriteBoolean("chat_peep_tracking", model->enable_chat_peep_tracking != 0); - writer->WriteBoolean("news", model->enable_news != 0); + writer->WriteBoolean("follower_peep_names", model->enable_follower_peep_names); + writer->WriteBoolean("follower_peep_tracking", model->enable_follower_peep_tracking); + writer->WriteBoolean("chat_peep_names", model->enable_chat_peep_names); + writer->WriteBoolean("chat_peep_tracking", model->enable_chat_peep_tracking); + writer->WriteBoolean("news", model->enable_news); } static void ReadFont(IIniReader * reader) diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index 5adf8efd3c..e4807da8a8 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -18,6 +18,238 @@ #include "../common.h" +typedef struct GeneralConfiguration +{ + // Paths + utf8 * rct1_path; + utf8 * rct2_path; + + // Display + sint32 window_width; + sint32 window_height; + sint32 fullscreen_mode; + sint32 fullscreen_width; + sint32 fullscreen_height; + float window_scale; + sint32 drawing_engine; + sint32 scale_quality; + bool use_nn_at_integer_scales; + bool uncap_fps; + bool show_fps; + bool minimize_fullscreen_focus_loss; + + // Map rendering + bool landscape_smoothing; + bool always_show_gridlines; + bool construction_marker_colour; + bool day_night_cycle; + bool enable_light_fx; + bool upper_case_banners; + bool render_weather_effects; + bool render_weather_gloom; + bool disable_lightning_effect; + + // Localisation + sint32 language; + sint32 measurement_format; + sint32 temperature_format; + bool show_height_as_units; + sint32 date_format; + sint32 currency_format; + sint32 custom_currency_rate; + sint32 custom_currency_affix; + utf8 * custom_currency_symbol; + + // Controls + bool edge_scrolling; + bool trap_cursor; + bool invert_viewport_drag; + bool zoom_to_cursor; + + // Miscellaneous + bool play_intro; + sint32 window_snap_proximity; + bool allow_loading_with_incorrect_checksum; + bool save_plugin_data; + bool test_unfinished_tracks; + bool no_test_crashes; + bool debugging_tools; + sint32 autosave_frequency; + bool auto_staff_placement; + bool handymen_mow_default; + bool auto_open_shops; + sint32 default_inspection_interval; + sint32 window_limit; + sint32 scenario_select_mode; + bool scenario_unlocking_enabled; + bool scenario_hide_mega_park; + bool steam_overlay_pause; + + bool confirmation_prompt; + sint32 load_save_sort; + utf8 * last_save_game_directory; + utf8 * last_save_landscape_directory; + utf8 * last_save_scenario_directory; + utf8 * last_save_track_directory; + utf8 * last_run_version; + + sint32 screenshot_format; +} GeneralConfiguration; + +typedef struct InterfaceConfiguration +{ + bool toolbar_show_finances; + bool toolbar_show_research; + bool toolbar_show_cheats; + bool toolbar_show_news; + bool select_by_track_type; + bool console_small_font; + utf8 * current_theme_preset; + utf8 * current_title_sequence_preset; + sint32 object_selection_filter_flags; +} InterfaceConfiguration; + +typedef struct SoundConfiguration +{ + utf8 * device; + uint8 master_volume; + uint8 title_music; + bool sound_enabled; + uint8 sound_volume; + bool ride_music_enabled; + uint8 ride_music_volume; + bool audio_focus; +} SoundConfiguration; + +typedef struct TwitchConfiguration +{ + utf8 * channel; + bool enable_follower_peep_names; + bool enable_follower_peep_tracking; + bool enable_chat_peep_names; + bool enable_chat_peep_tracking; + bool enable_news; +} TwitchConfiguration; + +typedef struct NetworkConfiguration +{ + utf8 * player_name; + sint32 default_port; + utf8 * default_password; + bool stay_connected; + bool advertise; + sint32 maxplayers; + utf8 * server_name; + utf8 * server_description; + utf8 * server_greeting; + utf8 * master_server_url; + utf8 * provider_name; + utf8 * provider_email; + utf8 * provider_website; + bool known_keys_only; + bool log_chat; +} NetworkConfiguration; + +typedef struct NotificationConfiguration +{ + bool park_award; + bool park_marketing_campaign_finished; + bool park_warnings; + bool park_rating_warnings; + bool ride_broken_down; + bool ride_crashed; + bool ride_warnings; + bool ride_researched; + bool guest_warnings; + bool guest_lost; + bool guest_left_park; + bool guest_queuing_for_ride; + bool guest_on_ride; + bool guest_left_ride; + bool guest_bought_item; + bool guest_used_facility; + bool guest_died; +} NotificationConfiguration; + +typedef struct FontConfiguration +{ + utf8 * file_name; + utf8 * font_name; + sint32 x_offset; + sint32 y_offset; + sint32 size_tiny; + sint32 size_small; + sint32 size_medium; + sint32 size_big; + sint32 height_tiny; + sint32 height_small; + sint32 height_medium; + sint32 height_big; +} FontConfiguration; + +extern GeneralConfiguration gConfigGeneral; +extern InterfaceConfiguration gConfigInterface; +extern SoundConfiguration gConfigSound; +extern TwitchConfiguration gConfigTwitch; +extern NetworkConfiguration gConfigNetwork; +extern NotificationConfiguration gConfigNotifications; +extern FontConfiguration gConfigFonts; + +enum AUTOSAVE +{ + AUTOSAVE_EVERY_MINUTE, + AUTOSAVE_EVERY_5MINUTES, + AUTOSAVE_EVERY_15MINUTES, + AUTOSAVE_EVERY_30MINUTES, + AUTOSAVE_EVERY_HOUR, + AUTOSAVE_NEVER +}; + +enum SORT +{ + SORT_NAME_ASCENDING, + SORT_NAME_DESCENDING, + SORT_DATE_ASCENDING, + SORT_DATE_DESCENDING, +}; + +enum SCENARIO_SELECT_MODE +{ + SCENARIO_SELECT_MODE_DIFFICULTY, + SCENARIO_SELECT_MODE_ORIGIN, +}; + +enum TEMPERATURE_FORMAT +{ + TEMPERATURE_FORMAT_C, + TEMPERATURE_FORMAT_F +}; + +enum MEASUREMENT_FORMAT +{ + MEASUREMENT_FORMAT_IMPERIAL, + MEASUREMENT_FORMAT_METRIC, + MEASUREMENT_FORMAT_SI +}; + +enum DATE_FORMAT +{ + DATE_FORMAT_DMY, + DATE_FORMAT_MDY, + DATE_FORMAT_YMD, + DATE_FORMAT_YDM +}; + +enum TITLE_SEQUENCE +{ + TITLE_SEQUENCE_RCT1, + TITLE_SEQUENCE_RCT1_AA, + TITLE_SEQUENCE_RCT1_AA_LL, + TITLE_SEQUENCE_RCT2, + TITLE_SEQUENCE_OPENRCT2, + TITLE_SEQUENCE_RANDOM +}; + extern "C" { bool config_open(const utf8 * path); diff --git a/src/openrct2/drawing/IDrawingEngine.h b/src/openrct2/drawing/IDrawingEngine.h index a4ded3b623..96cb70b387 100644 --- a/src/openrct2/drawing/IDrawingEngine.h +++ b/src/openrct2/drawing/IDrawingEngine.h @@ -23,6 +23,14 @@ struct rct_drawpixelinfo; interface IDrawingContext; +enum DRAWING_ENGINE +{ + DRAWING_ENGINE_NONE = -1, + DRAWING_ENGINE_SOFTWARE, + DRAWING_ENGINE_SOFTWARE_WITH_HARDWARE_DISPLAY, + DRAWING_ENGINE_OPENGL, +}; + enum DRAWING_ENGINE_FLAGS { DEF_NONE = 0, From 87e3a8f8b0489ba8ef2ad1101b419c52e96451cc Mon Sep 17 00:00:00 2001 From: Ted John Date: Sat, 18 Feb 2017 14:51:35 +0000 Subject: [PATCH 13/50] Move config enums to more suitable places --- src/openrct2/config.h | 12 ----------- src/openrct2/config/Config.cpp | 12 ++++++----- src/openrct2/config/Config.h | 34 -------------------------------- src/openrct2/scenario/scenario.h | 14 +++++++++++++ 4 files changed, 21 insertions(+), 51 deletions(-) diff --git a/src/openrct2/config.h b/src/openrct2/config.h index 5b161d5fb2..496ea118f1 100644 --- a/src/openrct2/config.h +++ b/src/openrct2/config.h @@ -21,13 +21,6 @@ #include "localisation/currency.h" #include "platform/platform.h" -enum { - CONFIG_FLAG_ALWAYS_SHOW_GRIDLINES = (1 << 0), - CONFIG_FLAG_SHOW_HEIGHT_AS_UNITS = (1 << 1), - CONFIG_FLAG_DISABLE_SMOOTH_LANDSCAPE = (1 << 2), - CONFIG_FLAG_SAVE_PLUGIN_DATA = (1 << 3) -}; - enum { SHORTCUT_CLOSE_TOP_MOST_WINDOW, SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS, @@ -98,15 +91,10 @@ void config_release(); bool config_open_default(); bool config_save_default(); -uint16 getLanguage(); - void config_reset_shortcut_keys(); bool config_shortcut_keys_load(); bool config_shortcut_keys_save(); bool config_find_or_browse_install_directory(); -void title_sequences_set_default(); -void title_sequences_load_presets(); - #endif diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index f3ed840f3a..a99282d867 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -27,7 +27,9 @@ extern "C" { #include "../localisation/currency.h" + #include "../localisation/date.h" #include "../localisation/language.h" + #include "../scenario/scenario.h" } namespace Config @@ -72,10 +74,10 @@ namespace Config static auto Enum_DateFormat = ConfigEnum( { - ConfigEnumEntry("DD/MM/YY", DATE_FORMAT_DMY), - ConfigEnumEntry("MM/DD/YY", DATE_FORMAT_MDY), - ConfigEnumEntry("YY/MM/DD", DATE_FORMAT_YMD), - ConfigEnumEntry("YY/DD/MM", DATE_FORMAT_YDM), + ConfigEnumEntry("DD/MM/YY", DATE_FORMAT_DAY_MONTH_YEAR), + ConfigEnumEntry("MM/DD/YY", DATE_FORMAT_MONTH_DAY_YEAR), + ConfigEnumEntry("YY/MM/DD", DATE_FORMAT_YEAR_MONTH_DAY), + ConfigEnumEntry("YY/DD/MM", DATE_FORMAT_YEAR_DAY_MONTH), }); static auto Enum_DrawingEngine = ConfigEnum( @@ -156,7 +158,7 @@ namespace Config model->test_unfinished_tracks = reader->GetBoolean("test_unfinished_tracks", false); model->no_test_crashes = reader->GetBoolean("no_test_crashes", false); - model->date_format = reader->GetEnum("date_format", DATE_FORMAT_DMY, Enum_DateFormat); + model->date_format = reader->GetEnum("date_format", DATE_FORMAT_DAY_MONTH_YEAR, Enum_DateFormat); model->auto_staff_placement = reader->GetBoolean("auto_staff", true); model->handymen_mow_default = reader->GetBoolean("handymen_mow_default", false); model->default_inspection_interval = reader->GetSint32("default_inspection_interval", 2); diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index e4807da8a8..4945802677 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -195,16 +195,6 @@ extern NetworkConfiguration gConfigNetwork; extern NotificationConfiguration gConfigNotifications; extern FontConfiguration gConfigFonts; -enum AUTOSAVE -{ - AUTOSAVE_EVERY_MINUTE, - AUTOSAVE_EVERY_5MINUTES, - AUTOSAVE_EVERY_15MINUTES, - AUTOSAVE_EVERY_30MINUTES, - AUTOSAVE_EVERY_HOUR, - AUTOSAVE_NEVER -}; - enum SORT { SORT_NAME_ASCENDING, @@ -213,12 +203,6 @@ enum SORT SORT_DATE_DESCENDING, }; -enum SCENARIO_SELECT_MODE -{ - SCENARIO_SELECT_MODE_DIFFICULTY, - SCENARIO_SELECT_MODE_ORIGIN, -}; - enum TEMPERATURE_FORMAT { TEMPERATURE_FORMAT_C, @@ -232,24 +216,6 @@ enum MEASUREMENT_FORMAT MEASUREMENT_FORMAT_SI }; -enum DATE_FORMAT -{ - DATE_FORMAT_DMY, - DATE_FORMAT_MDY, - DATE_FORMAT_YMD, - DATE_FORMAT_YDM -}; - -enum TITLE_SEQUENCE -{ - TITLE_SEQUENCE_RCT1, - TITLE_SEQUENCE_RCT1_AA, - TITLE_SEQUENCE_RCT1_AA_LL, - TITLE_SEQUENCE_RCT2, - TITLE_SEQUENCE_OPENRCT2, - TITLE_SEQUENCE_RANDOM -}; - extern "C" { bool config_open(const utf8 * path); diff --git a/src/openrct2/scenario/scenario.h b/src/openrct2/scenario/scenario.h index 468d1d82d0..f6959bda2f 100644 --- a/src/openrct2/scenario/scenario.h +++ b/src/openrct2/scenario/scenario.h @@ -343,6 +343,20 @@ enum { OBJECTIVE_MONTHLY_FOOD_INCOME }; +enum { + SCENARIO_SELECT_MODE_DIFFICULTY, + SCENARIO_SELECT_MODE_ORIGIN, +}; + +enum { + AUTOSAVE_EVERY_MINUTE, + AUTOSAVE_EVERY_5MINUTES, + AUTOSAVE_EVERY_15MINUTES, + AUTOSAVE_EVERY_30MINUTES, + AUTOSAVE_EVERY_HOUR, + AUTOSAVE_NEVER +}; + #define AUTOSAVE_PAUSE 0 extern const rct_string_id ScenarioCategoryStringIds[SCENARIO_CATEGORY_COUNT]; From 6bda8eba0f422dd3aa551bbcd2b06d6d50f93d6c Mon Sep 17 00:00:00 2001 From: Ted John Date: Sat, 18 Feb 2017 15:16:08 +0000 Subject: [PATCH 14/50] Move remaining config functions to C++ --- src/openrct2/config.c | 948 ------------------------------ src/openrct2/config/Config.cpp | 163 +++++ src/openrct2/config/IniReader.cpp | 39 ++ src/openrct2/config/IniReader.h | 1 + 4 files changed, 203 insertions(+), 948 deletions(-) diff --git a/src/openrct2/config.c b/src/openrct2/config.c index 2186bc470a..9dd68cf1bb 100644 --- a/src/openrct2/config.c +++ b/src/openrct2/config.c @@ -24,954 +24,6 @@ #include "OpenRCT2.h" #include "util/util.h" -enum { - CONFIG_VALUE_TYPE_BOOLEAN, - CONFIG_VALUE_TYPE_UINT8, - CONFIG_VALUE_TYPE_UINT16, - CONFIG_VALUE_TYPE_UINT32, - CONFIG_VALUE_TYPE_SINT8, - CONFIG_VALUE_TYPE_SINT16, - CONFIG_VALUE_TYPE_SINT32, - CONFIG_VALUE_TYPE_FLOAT, - CONFIG_VALUE_TYPE_DOUBLE, - CONFIG_VALUE_TYPE_STRING -}; - -size_t _configValueTypeSize[] = { - sizeof(bool), - sizeof(uint8), - sizeof(uint16), - sizeof(uint32), - sizeof(sint8), - sizeof(sint16), - sizeof(sint32), - sizeof(float), - sizeof(double), - sizeof(utf8string) -}; - -typedef union { - sint32 value_sint32; - - bool value_boolean; - sint8 value_sint8; - sint16 value_sint16; - uint8 value_uint8; - uint16 value_uint16; - uint32 value_uint32; - float value_float; - double value_double; - utf8string value_string; -} value_union; - -typedef struct config_enum_definition { - const_utf8string key; - value_union value; -} config_enum_definition; - -#define END_OF_ENUM { NULL, 0 } - -typedef struct config_property_definition { - size_t offset; - const_utf8string property_name; - uint8 type; - value_union default_value; - config_enum_definition *enum_definitions; -} config_property_definition; - -typedef struct config_section_definition { - void *base_address; - const_utf8string section_name; - config_property_definition *property_definitions; - sint32 property_definitions_count; -} config_section_definition; - -#pragma region Enum definitions - -config_enum_definition _drawingEngineFormatEnum[] = { - { "SOFTWARE", DRAWING_ENGINE_SOFTWARE }, - { "SOFTWARE_HWD", DRAWING_ENGINE_SOFTWARE_WITH_HARDWARE_DISPLAY }, - { "OPENGL", DRAWING_ENGINE_OPENGL }, - END_OF_ENUM -}; - -config_enum_definition _measurementFormatEnum[] = { - { "IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL }, - { "METRIC", MEASUREMENT_FORMAT_METRIC }, - { "SI", MEASUREMENT_FORMAT_SI }, - END_OF_ENUM -}; - -config_enum_definition _temperatureFormatEnum[] = { - { "CELSIUS", TEMPERATURE_FORMAT_C }, - { "FAHRENHEIT", TEMPERATURE_FORMAT_F }, - END_OF_ENUM -}; - -config_enum_definition _currencyEnum[] = { - { "GBP", CURRENCY_POUNDS }, - { "USD", CURRENCY_DOLLARS }, - { "FRF", CURRENCY_FRANC }, - { "DEM", CURRENCY_DEUTSCHMARK }, - { "JPY", CURRENCY_YEN }, - { "ESP", CURRENCY_PESETA }, - { "ITL", CURRENCY_LIRA }, - { "NLG", CURRENCY_GUILDERS }, - { "SEK", CURRENCY_KRONA }, - { "EUR", CURRENCY_EUROS }, - { "KRW", CURRENCY_WON }, - { "RUB", CURRENCY_ROUBLE }, - { "CZK", CURRENCY_CZECH_KORUNA }, - { "HKD", CURRENCY_HKD }, - { "TWD", CURRENCY_TWD }, - { "CNY", CURRENCY_YUAN }, - END_OF_ENUM -}; - -config_enum_definition _currencySymbolAffixEnum[] = { - { "PREFIX", CURRENCY_PREFIX }, - { "SUFFIX", CURRENCY_SUFFIX }, - END_OF_ENUM -}; - -config_enum_definition _languageEnum[] = { - { "en-GB", LANGUAGE_ENGLISH_UK }, - { "en-US", LANGUAGE_ENGLISH_US }, - { "de-DE", LANGUAGE_GERMAN }, - { "nl-NL", LANGUAGE_DUTCH }, - { "fr-FR", LANGUAGE_FRENCH }, - { "hu-HU", LANGUAGE_HUNGARIAN }, - { "pl-PL", LANGUAGE_POLISH }, - { "es-ES", LANGUAGE_SPANISH }, - { "sv-SE", LANGUAGE_SWEDISH }, - { "it-IT", LANGUAGE_ITALIAN }, - { "pt-BR", LANGUAGE_PORTUGUESE_BR }, - { "zh-TW", LANGUAGE_CHINESE_TRADITIONAL }, - { "zh-CN", LANGUAGE_CHINESE_SIMPLIFIED }, - { "fi-FI", LANGUAGE_FINNISH }, - { "ko-KR", LANGUAGE_KOREAN }, - { "ru-RU", LANGUAGE_RUSSIAN }, - { "cs-CZ", LANGUAGE_CZECH }, - { "ja-JP", LANGUAGE_JAPANESE }, - { "nb-NO", LANGUAGE_NORWEGIAN }, - { "ca-ES", LANGUAGE_CATALAN }, - END_OF_ENUM -}; - -config_enum_definition _dateFormatEnum[] = { - { "DD/MM/YY", DATE_FORMAT_DMY }, - { "MM/DD/YY", DATE_FORMAT_MDY }, - { "YY/MM/DD", DATE_FORMAT_YMD }, - { "YY/DD/MM", DATE_FORMAT_YDM }, - END_OF_ENUM -}; - -#pragma endregion - -#pragma region Section / property definitions - -config_property_definition _generalDefinitions[] = { - { offsetof(general_configuration, always_show_gridlines), "always_show_gridlines", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, autosave_frequency), "autosave", CONFIG_VALUE_TYPE_UINT8, AUTOSAVE_EVERY_5MINUTES, NULL }, - { offsetof(general_configuration, confirmation_prompt), "confirmation_prompt", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, construction_marker_colour), "construction_marker_colour", CONFIG_VALUE_TYPE_UINT8, false, NULL }, - { offsetof(general_configuration, currency_format), "currency_format", CONFIG_VALUE_TYPE_UINT8, CURRENCY_POUNDS, _currencyEnum }, - { offsetof(general_configuration, custom_currency_rate), "custom_currency_rate", CONFIG_VALUE_TYPE_SINT32, 10, NULL }, - { offsetof(general_configuration, custom_currency_affix), "custom_currency_affix", CONFIG_VALUE_TYPE_SINT8, CURRENCY_SUFFIX, _currencySymbolAffixEnum}, - { offsetof(general_configuration, custom_currency_symbol), "custom_currency_symbol", CONFIG_VALUE_TYPE_STRING, { .value_string = "Ctm" }, NULL }, - { offsetof(general_configuration, edge_scrolling), "edge_scrolling", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, fullscreen_mode), "fullscreen_mode", CONFIG_VALUE_TYPE_UINT8, 0, NULL }, - { offsetof(general_configuration, fullscreen_height), "fullscreen_height", CONFIG_VALUE_TYPE_SINT32, -1, NULL }, - { offsetof(general_configuration, fullscreen_width), "fullscreen_width", CONFIG_VALUE_TYPE_SINT32, -1, NULL }, - { offsetof(general_configuration, rct1_path), "rct1_path", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, rct2_path), "game_path", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, landscape_smoothing), "landscape_smoothing", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, language), "language", CONFIG_VALUE_TYPE_UINT16, LANGUAGE_ENGLISH_UK, _languageEnum }, - { offsetof(general_configuration, measurement_format), "measurement_format", CONFIG_VALUE_TYPE_UINT8, MEASUREMENT_FORMAT_METRIC, _measurementFormatEnum }, - { offsetof(general_configuration, play_intro), "play_intro", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, save_plugin_data), "save_plugin_data", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, debugging_tools), "debugging_tools", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, show_height_as_units), "show_height_as_units", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, temperature_format), "temperature_format", CONFIG_VALUE_TYPE_UINT8, TEMPERATURE_FORMAT_C, _temperatureFormatEnum }, - { offsetof(general_configuration, window_height), "window_height", CONFIG_VALUE_TYPE_SINT32, -1, NULL }, - { offsetof(general_configuration, window_snap_proximity), "window_snap_proximity", CONFIG_VALUE_TYPE_UINT8, 5, NULL }, - { offsetof(general_configuration, window_width), "window_width", CONFIG_VALUE_TYPE_SINT32, -1, NULL }, - { offsetof(general_configuration, drawing_engine), "drawing_engine", CONFIG_VALUE_TYPE_UINT8, DRAWING_ENGINE_SOFTWARE, _drawingEngineFormatEnum}, - { offsetof(general_configuration, uncap_fps), "uncap_fps", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, test_unfinished_tracks), "test_unfinished_tracks", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, //Default config setting is false until ghost trains are implemented #4540 - { offsetof(general_configuration, no_test_crashes), "no_test_crashes", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, date_format), "date_format", CONFIG_VALUE_TYPE_UINT8, DATE_FORMAT_DMY, _dateFormatEnum }, - { offsetof(general_configuration, auto_staff_placement), "auto_staff", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, handymen_mow_default), "handymen_mow_default", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, default_inspection_interval), "default_inspection_interval", CONFIG_VALUE_TYPE_UINT8, 2, NULL }, - { offsetof(general_configuration, last_run_version), "last_run_version", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, invert_viewport_drag), "invert_viewport_drag", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, load_save_sort), "load_save_sort", CONFIG_VALUE_TYPE_UINT8, SORT_NAME_ASCENDING, NULL }, - { offsetof(general_configuration, minimize_fullscreen_focus_loss), "minimize_fullscreen_focus_loss",CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, day_night_cycle), "day_night_cycle", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, //Default config setting is false until the games canvas can be seperated from the effect - { offsetof(general_configuration, enable_light_fx), "enable_light_fx", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, upper_case_banners), "upper_case_banners", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, disable_lightning_effect), "disable_lightning_effect", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, allow_loading_with_incorrect_checksum),"allow_loading_with_incorrect_checksum", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, steam_overlay_pause), "steam_overlay_pause", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, window_scale), "window_scale", CONFIG_VALUE_TYPE_FLOAT, { .value_float = 1.0f }, NULL }, - { offsetof(general_configuration, scale_quality), "scale_quality", CONFIG_VALUE_TYPE_UINT8, 1, NULL }, - { offsetof(general_configuration, use_nn_at_integer_scales), "use_nn_at_integer_scales", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, show_fps), "show_fps", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, trap_cursor), "trap_cursor", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, auto_open_shops), "auto_open_shops", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(general_configuration, scenario_select_mode), "scenario_select_mode", CONFIG_VALUE_TYPE_UINT8, SCENARIO_SELECT_MODE_ORIGIN, NULL }, - { offsetof(general_configuration, scenario_unlocking_enabled), "scenario_unlocking_enabled", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, scenario_hide_mega_park), "scenario_hide_mega_park", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, last_save_game_directory), "last_game_directory", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, last_save_landscape_directory), "last_landscape_directory", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, last_save_scenario_directory), "last_scenario_directory", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, last_save_track_directory), "last_track_directory", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(general_configuration, window_limit), "window_limit", CONFIG_VALUE_TYPE_UINT8, WINDOW_LIMIT_MAX, NULL }, - { offsetof(general_configuration, zoom_to_cursor), "zoom_to_cursor", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, render_weather_effects), "render_weather_effects", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(general_configuration, render_weather_gloom), "render_weather_gloom", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, -}; - -config_property_definition _interfaceDefinitions[] = { - { offsetof(interface_configuration, toolbar_show_finances), "toolbar_show_finances", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(interface_configuration, toolbar_show_research), "toolbar_show_research", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(interface_configuration, toolbar_show_cheats), "toolbar_show_cheats", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(interface_configuration, toolbar_show_news), "toolbar_show_news", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(interface_configuration, select_by_track_type), "select_by_track_type", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(interface_configuration, console_small_font), "console_small_font", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(interface_configuration, current_theme_preset), "current_theme", CONFIG_VALUE_TYPE_STRING, { .value_string = "*RCT2" }, NULL }, - { offsetof(interface_configuration, current_title_sequence_preset), "current_title_sequence", CONFIG_VALUE_TYPE_STRING, { .value_string = "*OPENRCT2" },NULL }, - { offsetof(interface_configuration, object_selection_filter_flags), "object_selection_filter_flags",CONFIG_VALUE_TYPE_UINT32, 0x7EF, NULL }, -}; - -config_property_definition _soundDefinitions[] = { - { offsetof(sound_configuration, master_volume), "master_volume", CONFIG_VALUE_TYPE_UINT8, 100, NULL }, - { offsetof(sound_configuration, title_music), "title_music", CONFIG_VALUE_TYPE_UINT8, 2, NULL }, - { offsetof(sound_configuration, sound_enabled), "sound", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(sound_configuration, sound_volume), "sound_volume", CONFIG_VALUE_TYPE_UINT8, 100, NULL }, - { offsetof(sound_configuration, ride_music_enabled), "ride_music", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(sound_configuration, ride_music_volume), "ride_music_volume", CONFIG_VALUE_TYPE_UINT8, 100, NULL }, - { offsetof(sound_configuration, audio_focus), "audio_focus", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(sound_configuration, device), "audio_device", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, -}; - -config_property_definition _twitchDefinitions[] = { - { offsetof(twitch_configuration, channel), "channel", CONFIG_VALUE_TYPE_STRING, { .value_string = NULL }, NULL }, - { offsetof(twitch_configuration, enable_follower_peep_names), "follower_peep_names", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(twitch_configuration, enable_follower_peep_tracking), "follower_peep_tracking", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(twitch_configuration, enable_chat_peep_names), "chat_peep_names", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(twitch_configuration, enable_chat_peep_tracking), "chat_peep_tracking", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(twitch_configuration, enable_news), "news", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL } -}; - -config_property_definition _networkDefinitions[] = { - { offsetof(network_configuration, player_name), "player_name", CONFIG_VALUE_TYPE_STRING, {.value_string = "Player" }, NULL }, - { offsetof(network_configuration, default_port), "default_port", CONFIG_VALUE_TYPE_UINT32, NETWORK_DEFAULT_PORT, NULL }, - { offsetof(network_configuration, default_password), "default_password", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, stay_connected), "stay_connected", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(network_configuration, advertise), "advertise", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(network_configuration, maxplayers), "maxplayers", CONFIG_VALUE_TYPE_UINT8, 16, NULL }, - { offsetof(network_configuration, server_name), "server_name", CONFIG_VALUE_TYPE_STRING, {.value_string = "Server" }, NULL }, - { offsetof(network_configuration, server_description), "server_description", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, server_greeting), "server_greeting", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, master_server_url), "master_server_url", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, provider_name), "provider_name", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, provider_email), "provider_email", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, provider_website), "provider_website", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(network_configuration, known_keys_only), "known_keys_only", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(network_configuration, log_chat), "log_chat", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, -}; - -config_property_definition _notificationsDefinitions[] = { - { offsetof(notification_configuration, park_award), "park_award", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, park_marketing_campaign_finished), "park_marketing_campaign_finished", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, park_warnings), "park_warnings", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, park_rating_warnings), "park_rating_warnings", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, ride_broken_down), "ride_broken_down", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, ride_crashed), "ride_crashed", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, ride_warnings), "ride_warnings", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, ride_researched), "ride_researched", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_warnings), "guest_warnings", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_lost), "guest_lost", CONFIG_VALUE_TYPE_BOOLEAN, false, NULL }, - { offsetof(notification_configuration, guest_left_park), "guest_entered_left_park", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_queuing_for_ride), "guest_queuing_for_ride", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_on_ride), "guest_on_ride", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_left_ride), "guest_left_ride", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_bought_item), "guest_bought_item", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_used_facility), "guest_used_facility", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, - { offsetof(notification_configuration, guest_died), "guest_died", CONFIG_VALUE_TYPE_BOOLEAN, true, NULL }, -}; - -config_property_definition _fontsDefinitions[] = { - { offsetof(font_configuration, file_name), "file_name", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(font_configuration, font_name), "font_name", CONFIG_VALUE_TYPE_STRING, {.value_string = NULL }, NULL }, - { offsetof(font_configuration, x_offset), "x_offset", CONFIG_VALUE_TYPE_SINT8, 0, NULL }, - { offsetof(font_configuration, y_offset), "y_offset", CONFIG_VALUE_TYPE_SINT8, -1, NULL }, - { offsetof(font_configuration, size_tiny), "size_tiny", CONFIG_VALUE_TYPE_UINT8, 8, NULL }, - { offsetof(font_configuration, size_small), "size_small", CONFIG_VALUE_TYPE_UINT8, 10, NULL }, - { offsetof(font_configuration, size_medium), "size_medium", CONFIG_VALUE_TYPE_UINT8, 11, NULL }, - { offsetof(font_configuration, size_big), "size_big", CONFIG_VALUE_TYPE_UINT8, 12, NULL }, - { offsetof(font_configuration, height_tiny), "height_tiny", CONFIG_VALUE_TYPE_UINT8, 6, NULL }, - { offsetof(font_configuration, height_small), "height_small", CONFIG_VALUE_TYPE_UINT8, 12, NULL }, - { offsetof(font_configuration, height_medium), "height_medium", CONFIG_VALUE_TYPE_UINT8, 12, NULL }, - { offsetof(font_configuration, height_big), "height_big", CONFIG_VALUE_TYPE_UINT8, 20, NULL } -}; - -config_section_definition _sectionDefinitions[] = { - { &gConfigGeneral, "general", _generalDefinitions, countof(_generalDefinitions) }, - { &gConfigInterface, "interface", _interfaceDefinitions, countof(_interfaceDefinitions) }, - { &gConfigSound, "sound", _soundDefinitions, countof(_soundDefinitions) }, - { &gConfigTwitch, "twitch", _twitchDefinitions, countof(_twitchDefinitions) }, - { &gConfigNetwork, "network", _networkDefinitions, countof(_networkDefinitions) }, - { &gConfigNotifications, "notifications", _notificationsDefinitions, countof(_notificationsDefinitions) }, - { &gConfigFonts, "fonts", _fontsDefinitions, countof(_fontsDefinitions) } -}; - -#pragma endregion - -general_configuration gConfigGeneral; -interface_configuration gConfigInterface; -sound_configuration gConfigSound; -twitch_configuration gConfigTwitch; -network_configuration gConfigNetwork; -notification_configuration gConfigNotifications; -font_configuration gConfigFonts; - -bool config_open(const utf8string path); -bool config_save(const utf8string path); -static void config_read_properties(config_section_definition **currentSection, const_utf8string line); -static void config_save_property_value(SDL_RWops *file, uint8 type, value_union *value); -static bool config_read_enum(void *dest, sint32 destSize, const utf8 *key, sint32 keySize, config_enum_definition *enumDefinitions); -static void config_write_enum(SDL_RWops *file, uint8 type, value_union *value, config_enum_definition *enumDefinitions); - -static void utf8_skip_whitespace(utf8 **outch); -static void utf8_skip_non_whitespace(utf8 **outch); - -static sint32 rwopsreadc(SDL_RWops *file) -{ - sint32 c = 0; - if (SDL_RWread(file, &c, 1, 1) != 1) - c = EOF; - return c; -} - -static void rwopswritec(SDL_RWops *file, char c) -{ - SDL_RWwrite(file, &c, 1, 1); -} - -static void rwopswritestr(SDL_RWops *file, const char *str) -{ - SDL_RWwrite(file, str, strlen(str), 1); -} - -static void rwopsprintf(SDL_RWops *file, const char *format, ...) -{ - va_list args; - va_start(args, format); - - char buffer[64]; - vsnprintf(buffer, 64, format, args); - - SDL_RWwrite(file, buffer, strlen(buffer), 1); - - va_end(args); -} - -static void rwopswritenewline(SDL_RWops *file) -{ - rwopswritestr(file, PLATFORM_NEWLINE); -} - -static void rwopswritestresc(SDL_RWops *file, const char *str) { - sint32 length = 0; - for (const char *c = str; *c != '\0'; ++c) { - if (*c == '\\') length += 2; - else ++length; - } - - char *escaped = malloc(length + 1); - sint32 j=0; - for (const char *c = str; *c != '\0'; ++c) { - if (*c == '\\') escaped[j++] = '\\'; - escaped[j++] = *c; - } - escaped[length] = '\0'; - - rwopswritestr(file, escaped); - SafeFree(escaped); -} - -void config_set_defaults() -{ - sint32 i, j; - - for (i = 0; i < countof(_sectionDefinitions); i++) { - config_section_definition *section = &_sectionDefinitions[i]; - for (j = 0; j < section->property_definitions_count; j++) { - config_property_definition *property = §ion->property_definitions[j]; - value_union *destValue = (value_union*)((size_t)section->base_address + (size_t)property->offset); - - // Special dynamic defaults - if (strcmp(property->property_name, "language") == 0){ - destValue->value_uint16 = platform_get_locale_language(); - if (destValue->value_uint16 == LANGUAGE_UNDEFINED) - memcpy(destValue, &property->default_value, _configValueTypeSize[property->type]); - } - else if (strcmp(property->property_name, "currency_format") == 0){ - destValue->value_uint8 = platform_get_locale_currency(); - } - else if (strcmp(property->property_name, "measurement_format") == 0){ - destValue->value_uint8 = platform_get_locale_measurement_format(); - } - else if (strcmp(property->property_name, "temperature_format") == 0){ - destValue->value_uint8 = platform_get_locale_temperature_format(); - } - else if (strcmp(property->property_name, "player_name") == 0) { - utf8* username = platform_get_username(); - - if (username) { - destValue->value_string = _strdup(username); - } else { - destValue->value_string = _strdup(language_get_string(STR_MULTIPLAYER_DEFAULT_NAME)); - } - } - else { - // Use static default - if (property->type == CONFIG_VALUE_TYPE_STRING) { - // Copy the string to new memory - const utf8 *src = property->default_value.value_string; - const utf8 **dst = (const utf8**)&(destValue->value_string); - if (src != NULL) { - *dst = _strdup(property->default_value.value_string); - } - } else { - memcpy(destValue, &property->default_value, _configValueTypeSize[property->type]); - } - } - } - } -} - -void config_release() -{ - for (sint32 i = 0; i < countof(_sectionDefinitions); i++) { - config_section_definition *section = &_sectionDefinitions[i]; - for (sint32 j = 0; j < section->property_definitions_count; j++) { - config_property_definition *property = §ion->property_definitions[j]; - value_union *destValue = (value_union*)((size_t)section->base_address + (size_t)property->offset); - if (property->type == CONFIG_VALUE_TYPE_STRING) { - utf8 **dst = (utf8**)&(destValue->value_string); - SafeFree(*dst); - } - } - } -} - -void config_get_default_path(utf8 *outPath, size_t size) -{ - platform_get_user_directory(outPath, NULL, size); - safe_strcat_path(outPath, "config.ini", size); -} - -bool config_open_default() -{ - utf8 path[MAX_PATH]; - - config_get_default_path(path, sizeof(path)); - if (config_open(path)) { - currency_load_custom_currency_config(); - return true; - } - - return false; -} - -bool config_save_default() -{ - utf8 path[MAX_PATH]; - - config_get_default_path(path, sizeof(path)); - if (config_save(path)) { - return true; - } - - return false; -} - -static bool config_open_2(const utf8string path) -{ - SDL_RWops *file; - utf8string lineBuffer; - size_t lineBufferCapacity; - size_t lineLength; - sint32 c; - config_section_definition *currentSection; - - file = SDL_RWFromFile(path, "rb"); - if (file == NULL) - return false; - - currentSection = NULL; - lineBufferCapacity = 64; - lineBuffer = malloc(lineBufferCapacity); - lineLength = 0; - - // Skim UTF-8 byte order mark - SDL_RWread(file, lineBuffer, 3, 1); - if (!utf8_is_bom(lineBuffer)) - SDL_RWseek(file, 0, RW_SEEK_SET); - - while ((c = rwopsreadc(file)) != EOF) { - if (c == '\n' || c == '\r') { - lineBuffer[lineLength] = 0; - config_read_properties(¤tSection, (const_utf8string)lineBuffer); - lineLength = 0; - } else { - lineBuffer[lineLength++] = c; - } - - if (lineLength >= lineBufferCapacity) { - lineBufferCapacity *= 2; - lineBuffer = realloc(lineBuffer, lineBufferCapacity); - } - } - - if (lineLength > 0) { - lineBuffer[lineLength++] = 0; - config_read_properties(¤tSection, lineBuffer); - } - - free(lineBuffer); - SDL_RWclose(file); - - // Window limit must be kept within valid range. - if (gConfigGeneral.window_limit < WINDOW_LIMIT_MIN) { - gConfigGeneral.window_limit = WINDOW_LIMIT_MIN; - } - else if (gConfigGeneral.window_limit > WINDOW_LIMIT_MAX) { - gConfigGeneral.window_limit = WINDOW_LIMIT_MAX; - } - - return true; -} - -static bool config_save_2(const utf8string path) -{ - SDL_RWops *file; - sint32 i, j; - value_union *value; - - file = SDL_RWFromFile(path, "wb"); - if (file == NULL) { - log_error("Unable to write to config file."); - return false; - } - - for (i = 0; i < countof(_sectionDefinitions); i++) { - config_section_definition *section = &_sectionDefinitions[i]; - - rwopswritec(file, '['); - rwopswritestr(file, section->section_name); - rwopswritec(file, ']'); - rwopswritenewline(file); - - for (j = 0; j < section->property_definitions_count; j++) { - config_property_definition *property = §ion->property_definitions[j]; - - rwopswritestr(file, property->property_name); - rwopswritestr(file, " = "); - - value = (value_union*)((size_t)section->base_address + (size_t)property->offset); - if (property->enum_definitions != NULL) - config_write_enum(file, property->type, value, property->enum_definitions); - else - config_save_property_value(file, property->type, value); - rwopswritenewline(file); - } - rwopswritenewline(file); - } - - SDL_RWclose(file); - return true; -} - -static void config_save_property_value(SDL_RWops *file, uint8 type, value_union *value) -{ - switch (type) { - case CONFIG_VALUE_TYPE_BOOLEAN: - if (value->value_boolean) rwopswritestr(file, "true"); - else rwopswritestr(file, "false"); - break; - case CONFIG_VALUE_TYPE_UINT8: - rwopsprintf(file, "%u", value->value_uint8); - break; - case CONFIG_VALUE_TYPE_UINT16: - rwopsprintf(file, "%u", value->value_uint16); - break; - case CONFIG_VALUE_TYPE_UINT32: - rwopsprintf(file, "%lu", value->value_uint32); - break; - case CONFIG_VALUE_TYPE_SINT8: - rwopsprintf(file, "%d", value->value_sint8); - break; - case CONFIG_VALUE_TYPE_SINT16: - rwopsprintf(file, "%d", value->value_sint16); - break; - case CONFIG_VALUE_TYPE_SINT32: - rwopsprintf(file, "%ld", value->value_sint32); - break; - case CONFIG_VALUE_TYPE_FLOAT: - rwopsprintf(file, "%.3f", value->value_float); - break; - case CONFIG_VALUE_TYPE_DOUBLE: - rwopsprintf(file, "%.6f", value->value_double); - break; - case CONFIG_VALUE_TYPE_STRING: - rwopswritec(file, '"'); - if (value->value_string != NULL) { - rwopswritestresc(file, value->value_string); - } - rwopswritec(file, '"'); - break; - } -} - -static bool config_get_section(const utf8string line, const utf8 **sectionName, sint32 *sectionNameSize) -{ - utf8 *ch; - sint32 c; - - ch = line; - utf8_skip_whitespace(&ch); - if (*ch != '[') return false; - *sectionName = ++ch; - - while ((c = utf8_get_next(ch, (const utf8**)&ch)) != 0) { - if (c == '#') return false; - if (c == '[') return false; - if (c == ' ') break; - if (c == ']') break; - } - - *sectionNameSize = (sint32)(ch - *sectionName - 1); - return true; -} - -static bool config_get_property_name_value(const utf8string line, utf8 **propertyName, sint32 *propertyNameSize, utf8 **value, sint32 *valueSize) -{ - utf8 *ch, *clast; - sint32 c; - bool quotes; - - ch = line; - utf8_skip_whitespace(&ch); - - if (*ch == 0) return false; - *propertyName = ch; - - bool equals = false; - while ((c = utf8_get_next(ch, (const utf8**)&ch)) != 0) { - if (isspace(c) || c == '=') { - if (c == '=') equals = true; - *propertyNameSize = (sint32)(ch - *propertyName - 1); - break; - } else if (c == '#') { - return false; - } - } - - if (*ch == 0) return false; - utf8_skip_whitespace(&ch); - if (!equals) { - if (*ch != '=') return false; - ch++; - utf8_skip_whitespace(&ch); - } - if (*ch == 0) return false; - - if (*ch == '"') { - ch++; - quotes = true; - } else { - quotes = false; - } - *value = ch; - - clast = ch; - while ((c = utf8_get_next(ch, (const utf8**)&ch)) != 0) { - if (!quotes) { - if (c == '#') break; - if (c != ' ') clast = ch; - } - } - if (!quotes) *valueSize = (sint32)(clast - *value); - else *valueSize = (sint32)(ch - *value - 1); - if (quotes) (*valueSize)--; - return true; -} - -static config_section_definition *config_get_section_def(const utf8 *name, sint32 size) -{ - sint32 i; - - for (i = 0; i < countof(_sectionDefinitions); i++) { - const_utf8string sectionName = _sectionDefinitions[i].section_name; - sint32 sectionNameSize = (sint32)strnlen(sectionName, size); - if (sectionNameSize == size && sectionName[size] == 0 && _strnicmp(sectionName, name, size) == 0) - return &_sectionDefinitions[i]; - } - - return NULL; -} - -static config_property_definition *config_get_property_def(config_section_definition *section, const utf8 *name, sint32 size) -{ - sint32 i; - - for (i = 0; i < section->property_definitions_count; i++) { - const_utf8string propertyName = section->property_definitions[i].property_name; - sint32 propertyNameSize = (sint32)strnlen(propertyName, size); - if (propertyNameSize == size && propertyName[size] == 0 && _strnicmp(propertyName, name, size) == 0) - { - return §ion->property_definitions[i]; - } - } - - return NULL; -} - -static utf8string escape_string(const utf8 *value, sint32 valueSize) { - sint32 length = 0; - bool backslash = false; - for (sint32 i=0; i < valueSize; ++i) { - if (value[i] == '\\') { - if (backslash) backslash = false; - else ++length, backslash = true; - } else ++length, backslash = false; - } - utf8string escaped = malloc(length + 1); - - sint32 j=0; - backslash = false; - for (sint32 i=0; i < valueSize; ++i) { - if (value[i] == '\\') { - if (backslash) backslash = false; - else escaped[j++] = value[i], backslash = true; - } else escaped[j++] = value[i], backslash = false; - } - escaped[length] = '\0'; - - return escaped; -} - -static void config_set_property(const config_section_definition *section, const config_property_definition *property, const utf8 *value, sint32 valueSize) -{ - value_union *destValue = (value_union*)((size_t)section->base_address + (size_t)property->offset); - - if (property->enum_definitions != NULL) - if (config_read_enum(destValue, (sint32)_configValueTypeSize[property->type], value, valueSize, property->enum_definitions)) - return; - - switch (property->type) { - case CONFIG_VALUE_TYPE_BOOLEAN: - if (_strnicmp(value, "false", valueSize) == 0) destValue->value_boolean = false; - else if (_strnicmp(value, "true", valueSize) == 0) destValue->value_boolean = true; - else destValue->value_boolean = strtol(value, NULL, 0) != 0; - break; - case CONFIG_VALUE_TYPE_UINT8: - destValue->value_uint8 = (uint8)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_UINT16: - destValue->value_uint16 = (uint16)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_UINT32: - destValue->value_uint32 = (uint32)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_SINT8: - destValue->value_sint8 = (sint8)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_SINT16: - destValue->value_sint16 = (sint16)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_SINT32: - destValue->value_sint32 = (sint32)strtol(value, NULL, 0); - break; - case CONFIG_VALUE_TYPE_FLOAT: - destValue->value_float = strtof(value, NULL); - break; - case CONFIG_VALUE_TYPE_DOUBLE: - destValue->value_double = strtod(value, NULL); - break; - case CONFIG_VALUE_TYPE_STRING: - SafeFree(destValue->value_string); - destValue->value_string = escape_string(value, valueSize); - break; - } -} - -static void config_read_properties(config_section_definition **currentSection, const_utf8string line) -{ - utf8 *ch = (utf8*)line; - utf8_skip_whitespace(&ch); - - if (*ch == '[') { - const utf8 *sectionName; - sint32 sectionNameSize; - if (config_get_section(ch, §ionName, §ionNameSize)) - *currentSection = config_get_section_def(sectionName, sectionNameSize); - } else { - if (*currentSection != NULL) { - utf8 *propertyName, *value; - sint32 propertyNameSize = 0, valueSize; - if (config_get_property_name_value(ch, &propertyName, &propertyNameSize, &value, &valueSize)) { - config_property_definition *property; - property = config_get_property_def(*currentSection, propertyName, propertyNameSize); - if (property != NULL) - config_set_property(*currentSection, property, value, valueSize); - } - } - } -} - -static bool config_read_enum(void *dest, sint32 destSize, const utf8 *key, sint32 keySize, config_enum_definition *enumDefinitions) -{ - while (enumDefinitions->key != NULL) { - if (strlen(enumDefinitions->key) == (size_t)keySize && _strnicmp(enumDefinitions->key, key, keySize) == 0) { - memcpy(dest, &enumDefinitions->value.value_uint32, destSize); - return true; - } - enumDefinitions++; - } - return false; -} - -static void config_write_enum(SDL_RWops *file, uint8 type, value_union *value, config_enum_definition *enumDefinitions) -{ - uint32 enumValue = (value->value_uint32) & ((1 << (_configValueTypeSize[type] * 8)) - 1); - while (enumDefinitions->key != NULL) { - if (enumDefinitions->value.value_uint32 == enumValue) { - rwopswritestr(file, enumDefinitions->key); - return; - } - enumDefinitions++; - } - config_save_property_value(file, type, value); -} - -static void utf8_skip_whitespace(utf8 **outch) -{ - utf8 *ch; - while (**outch != 0) { - ch = *outch; - if (!isspace(utf8_get_next(*outch, (const utf8**)outch))) { - *outch = ch; - break; - } - } -} - -static void utf8_skip_non_whitespace(utf8 **outch) -{ - while (**outch != 0) { - if (isspace(utf8_get_next(*outch, (const utf8**)outch))) - break; - } -} - -/* - -Code reserved for when we want more intelligent saving of config file which preserves comments and layout - -enum { - CONFIG_LINE_TYPE_WHITESPACE, - CONFIG_LINE_TYPE_COMMENT, - CONFIG_LINE_TYPE_SECTION, - CONFIG_LINE_TYPE_PROPERTY, - CONFIG_LINE_TYPE_INVALID -}; - -typedef struct { - uint8 type; - utf8string line; -} config_line; - -static config_line *_configLines = NULL; - -*/ - -/** - * Attempts to find the RCT2 installation directory. - * This should be created from some other resource when OpenRCT2 grows. - * @param resultPath Pointer to where the absolute path of the RCT2 installation directory will be copied to. - * @returns 1 if successful, otherwise 0. - */ -static bool config_find_rct2_path(utf8 *resultPath) -{ - sint32 i; - - log_verbose("searching common installation locations."); - - const utf8 *searchLocations[] = { - "C:\\Program Files\\Infogrames\\RollerCoaster Tycoon 2", - "C:\\Program Files (x86)\\Infogrames\\RollerCoaster Tycoon 2", - "C:\\Program Files\\Infogrames Interactive\\RollerCoaster Tycoon 2", - "C:\\Program Files (x86)\\Infogrames Interactive\\RollerCoaster Tycoon 2", - "C:\\Program Files\\Atari\\RollerCoaster Tycoon 2", - "C:\\Program Files (x86)\\Atari\\RollerCoaster Tycoon 2", - "C:\\GOG Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", - "C:\\Program Files\\GalaxyClient\\Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", - "C:\\Program Files (x86)\\GalaxyClient\\Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", - "C:\\Program Files\\Steam\\steamapps\\common\\Rollercoaster Tycoon 2", - "C:\\Program Files (x86)\\Steam\\steamapps\\common\\Rollercoaster Tycoon 2", - gExePath - }; - - for (i = 0; i < countof(searchLocations); i++) { - if (platform_original_game_data_exists(searchLocations[i])) { - safe_strcpy(resultPath, searchLocations[i], MAX_PATH); - return true; - } - } - - return false; -} - -bool config_find_or_browse_install_directory() -{ - utf8 path[MAX_PATH]; - utf8 *installPath; - - if (config_find_rct2_path(path)) { - SafeFree(gConfigGeneral.rct2_path); - gConfigGeneral.rct2_path = malloc(strlen(path) + 1); - safe_strcpy(gConfigGeneral.rct2_path, path, MAX_PATH); - } else { - if (gOpenRCT2Headless) { - return false; - } - while (1) { - platform_show_messagebox("OpenRCT2 needs files from the original RollerCoaster Tycoon 2 in order to work. Please select the directory where you installed RollerCoaster Tycoon 2."); - installPath = platform_open_directory_browser("Please select your RCT2 directory"); - if (installPath == NULL) - return false; - - SafeFree(gConfigGeneral.rct2_path); - gConfigGeneral.rct2_path = installPath; - - if (platform_original_game_data_exists(installPath)) - return true; - - utf8 message[MAX_PATH]; - snprintf(message, MAX_PATH, "Could not find %s" PATH_SEPARATOR "Data" PATH_SEPARATOR "g1.dat at this path", installPath); - platform_show_messagebox(message); - } - } - - return true; -} - #pragma region Shortcuts // Current keyboard shortcuts diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index a99282d867..0ba2d67294 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -17,9 +17,13 @@ #include #include "../core/Console.hpp" #include "../core/Exception.hpp" +#include "../core/Memory.hpp" +#include "../core/Path.hpp" +#include "../core/String.hpp" #include "../drawing/IDrawingEngine.h" #include "../interface/window.h" #include "../network/network.h" +#include "../OpenRCT2.h" #include "Config.h" #include "IniReader.h" #include "IniWriter.h" @@ -479,6 +483,26 @@ namespace Config writer->WriteSint32("height_big", model->height_big); } + static bool SetDefaults() + { + try + { + auto reader = std::unique_ptr(CreateDefaultIniReader()); + ReadGeneral(reader.get()); + ReadInterface(reader.get()); + ReadSound(reader.get()); + ReadNetwork(reader.get()); + ReadNotifications(reader.get()); + ReadTwitch(reader.get()); + ReadFont(reader.get()); + return true; + } + catch (const Exception &) + { + return false; + } + } + static bool ReadFile(const std::string &path) { try @@ -520,10 +544,54 @@ namespace Config return false; } } + + /** + * Attempts to find the RCT2 installation directory. + * This should be created from some other resource when OpenRCT2 grows. + * @param resultPath Pointer to where the absolute path of the RCT2 installation directory will be copied to. + * @returns 1 if successful, otherwise 0. + */ + static std::string FindRCT2Path() + { + log_verbose("config_find_rct2_path(...)"); + + static const utf8 * searchLocations[] = + { + "C:\\GOG Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", + "C:\\Program Files\\Atari\\RollerCoaster Tycoon 2", + "C:\\Program Files\\GalaxyClient\\Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", + "C:\\Program Files\\Infogrames\\RollerCoaster Tycoon 2", + "C:\\Program Files\\Infogrames Interactive\\RollerCoaster Tycoon 2", + "C:\\Program Files\\Steam\\steamapps\\common\\Rollercoaster Tycoon 2", + "C:\\Program Files (x86)\\Atari\\RollerCoaster Tycoon 2", + "C:\\Program Files (x86)\\GalaxyClient\\Games\\RollerCoaster Tycoon 2 Triple Thrill Pack", + "C:\\Program Files (x86)\\Infogrames\\RollerCoaster Tycoon 2", + "C:\\Program Files (x86)\\Infogrames Interactive\\RollerCoaster Tycoon 2", + "C:\\Program Files (x86)\\Steam\\steamapps\\common\\Rollercoaster Tycoon 2" + }; + + for (const utf8 * location : searchLocations) + { + if (platform_original_game_data_exists(location)) + { + return location; + } + } + if (platform_original_game_data_exists(gExePath)) + { + return gExePath; + } + return std::string(); + } } extern "C" { + void config_set_defaults() + { + Config::SetDefaults(); + } + bool config_open(const utf8 * path) { return Config::ReadFile(path); @@ -533,4 +601,99 @@ extern "C" { return Config::WriteFile(path); } + + void config_release() + { + SafeFree(gConfigGeneral.rct1_path); + SafeFree(gConfigGeneral.rct2_path); + SafeFree(gConfigGeneral.custom_currency_symbol); + SafeFree(gConfigGeneral.last_save_game_directory); + SafeFree(gConfigGeneral.last_save_landscape_directory); + SafeFree(gConfigGeneral.last_save_scenario_directory); + SafeFree(gConfigGeneral.last_save_track_directory); + SafeFree(gConfigGeneral.last_run_version); + SafeFree(gConfigInterface.current_theme_preset); + SafeFree(gConfigInterface.current_title_sequence_preset); + SafeFree(gConfigSound.device); + SafeFree(gConfigTwitch.channel); + SafeFree(gConfigNetwork.player_name); + SafeFree(gConfigNetwork.default_password); + SafeFree(gConfigNetwork.server_name); + SafeFree(gConfigNetwork.server_description); + SafeFree(gConfigNetwork.server_greeting); + SafeFree(gConfigNetwork.master_server_url); + SafeFree(gConfigNetwork.provider_name); + SafeFree(gConfigNetwork.provider_email); + SafeFree(gConfigNetwork.provider_website); + SafeFree(gConfigFonts.file_name); + SafeFree(gConfigFonts.font_name); + } + + void config_get_default_path(utf8 * outPath, size_t size) + { + platform_get_user_directory(outPath, nullptr, size); + Path::Append(outPath, size, "config.ini"); + } + + bool config_open_default() + { + utf8 path[MAX_PATH]; + config_get_default_path(path, sizeof(path)); + if (config_open(path)) + { + currency_load_custom_currency_config(); + return true; + } + return false; + } + + bool config_save_default() + { + utf8 path[MAX_PATH]; + config_get_default_path(path, sizeof(path)); + if (config_save(path)) + { + return true; + } + return false; + } + + bool config_find_or_browse_install_directory() + { + std::string path = Config::FindRCT2Path(); + if (!path.empty()) + { + Memory::Free(gConfigGeneral.rct2_path); + gConfigGeneral.rct2_path = String::Duplicate(path.c_str()); + } + else + { + if (gOpenRCT2Headless) + { + return false; + } + while (1) + { + platform_show_messagebox("OpenRCT2 needs files from the original RollerCoaster Tycoon 2 in order to work. Please select the directory where you installed RollerCoaster Tycoon 2."); + utf8 * installPath = platform_open_directory_browser("Please select your RCT2 directory"); + if (installPath == nullptr) + { + return false; + } + + Memory::Free(gConfigGeneral.rct2_path); + gConfigGeneral.rct2_path = installPath; + + if (platform_original_game_data_exists(installPath)) + { + return true; + } + + utf8 message[MAX_PATH]; + snprintf(message, MAX_PATH, "Could not find %s" PATH_SEPARATOR "Data" PATH_SEPARATOR "g1.dat at this path", installPath); + platform_show_messagebox(message); + } + } + return true; + } } diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 300eae90b2..d203650f01 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -323,6 +323,40 @@ private: } }; +class DefaultIniReader final : public IIniReader +{ +public: + bool ReadSection(const std::string &name) override + { + return true; + } + + bool GetBoolean(const std::string &name, bool defaultValue) const override + { + return defaultValue; + } + + sint32 GetSint32(const std::string &name, sint32 defaultValue) const override + { + return defaultValue; + } + + float GetFloat(const std::string &name, float defaultValue) const override + { + return defaultValue; + } + + std::string GetString(const std::string &name, const std::string &defaultValue) const override + { + return defaultValue; + } + + bool TryGetString(const std::string &name, std::string * outValue) const override + { + return false; + } +}; + utf8 * IIniReader::GetCString(const std::string &name, const utf8 * defaultValue) const { std::string szValue; @@ -338,3 +372,8 @@ IIniReader * CreateIniReader(const std::string &path) { return new IniReader(path); } + +IIniReader * CreateDefaultIniReader() +{ + return new DefaultIniReader(); +} diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.h index 5df6e1dc7a..9a2cf66d06 100644 --- a/src/openrct2/config/IniReader.h +++ b/src/openrct2/config/IniReader.h @@ -46,3 +46,4 @@ interface IIniReader }; IIniReader * CreateIniReader(const std::string &path); +IIniReader * CreateDefaultIniReader(); From 4457749b35d6135a9e3cecef08e0d8a38961e249 Mon Sep 17 00:00:00 2001 From: Ted John Date: Sat, 18 Feb 2017 15:30:54 +0000 Subject: [PATCH 15/50] Move keyboard shortcut loading to C++ --- src/openrct2/config.c | 159 -------------------- src/openrct2/config.h | 100 ------------- src/openrct2/config/Config.h | 6 + src/openrct2/config/KeyboardShortcuts.cpp | 165 +++++++++++++++++++++ src/openrct2/interface/keyboard_shortcut.h | 68 +++++++++ src/openrct2/libopenrct2.vcxproj | 3 +- 6 files changed, 240 insertions(+), 261 deletions(-) delete mode 100644 src/openrct2/config.c delete mode 100644 src/openrct2/config.h create mode 100644 src/openrct2/config/KeyboardShortcuts.cpp diff --git a/src/openrct2/config.c b/src/openrct2/config.c deleted file mode 100644 index 9dd68cf1bb..0000000000 --- a/src/openrct2/config.c +++ /dev/null @@ -1,159 +0,0 @@ -#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers -/***************************************************************************** - * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. - * - * OpenRCT2 is the work of many authors, a full list can be found in contributors.md - * For more information, visit https://github.com/OpenRCT2/OpenRCT2 - * - * OpenRCT2 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. - * - * A full copy of the GNU General Public License can be found in licence.txt - *****************************************************************************/ -#pragma endregion - -#include "config.h" -#include "interface/keyboard_shortcut.h" -#include "interface/themes.h" -#include "interface/viewport.h" -#include "localisation/language.h" -#include "localisation/localisation.h" -#include "network/network.h" -#include "OpenRCT2.h" -#include "util/util.h" - -#pragma region Shortcuts - -// Current keyboard shortcuts -uint16 gShortcutKeys[SHORTCUT_COUNT]; - -// Default keyboard shortcuts -static const uint16 _defaultShortcutKeys[SHORTCUT_COUNT] = { - SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_TOP_MOST_WINDOW - SHIFT | SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS - SDL_SCANCODE_ESCAPE, // SHORTCUT_CANCEL_CONSTRUCTION_MODE - SDL_SCANCODE_PAUSE, // SHORTCUT_PAUSE_GAME - SDL_SCANCODE_PAGEUP, // SHORTCUT_ZOOM_VIEW_OUT - SDL_SCANCODE_PAGEDOWN, // SHORTCUT_ZOOM_VIEW_IN - SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_CLOCKWISE - SHIFT | SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE - SDL_SCANCODE_Z, // SHORTCUT_ROTATE_CONSTRUCTION_OBJECT - SDL_SCANCODE_1, // SHORTCUT_UNDERGROUND_VIEW_TOGGLE - SDL_SCANCODE_H, // SHORTCUT_REMOVE_BASE_LAND_TOGGLE - SDL_SCANCODE_V, // SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE - SDL_SCANCODE_3, // SHORTCUT_SEE_THROUGH_RIDES_TOGGLE - SDL_SCANCODE_4, // SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE - SDL_SCANCODE_5, // SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE - SDL_SCANCODE_6, // SHORTCUT_INVISIBLE_PEOPLE_TOGGLE - SDL_SCANCODE_8, // SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE - SDL_SCANCODE_9, // SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE - SDL_SCANCODE_0, // SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE - SDL_SCANCODE_F1, // SHORTCUT_ADJUST_LAND - SDL_SCANCODE_F2, // SHORTCUT_ADJUST_WATER - SDL_SCANCODE_F3, // SHORTCUT_BUILD_SCENERY - SDL_SCANCODE_F4, // SHORTCUT_BUILD_PATHS - SDL_SCANCODE_F5, // SHORTCUT_BUILD_NEW_RIDE - SDL_SCANCODE_F, // SHORTCUT_SHOW_FINANCIAL_INFORMATION - SDL_SCANCODE_D, // SHORTCUT_SHOW_RESEARCH_INFORMATION - SDL_SCANCODE_R, // SHORTCUT_SHOW_RIDES_LIST - SDL_SCANCODE_P, // SHORTCUT_SHOW_PARK_INFORMATION - SDL_SCANCODE_G, // SHORTCUT_SHOW_GUEST_LIST - SDL_SCANCODE_S, // SHORTCUT_SHOW_STAFF_LIST - SDL_SCANCODE_M, // SHORTCUT_SHOW_RECENT_MESSAGES - SDL_SCANCODE_TAB, // SHORTCUT_SHOW_MAP - PLATFORM_MODIFIER | SDL_SCANCODE_S, // SHORTCUT_SCREENSHOT - - // New - SDL_SCANCODE_MINUS, // SHORTCUT_REDUCE_GAME_SPEED, - SDL_SCANCODE_EQUALS, // SHORTCUT_INCREASE_GAME_SPEED, - PLATFORM_MODIFIER | ALT | SDL_SCANCODE_C, // SHORTCUT_OPEN_CHEAT_WINDOW, - SDL_SCANCODE_T, // SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, - SDL_SCANCODE_UP, // SHORTCUT_SCROLL_MAP_UP - SDL_SCANCODE_LEFT, // SHORTCUT_SCROLL_MAP_LEFT - SDL_SCANCODE_DOWN, // SHORTCUT_SCROLL_MAP_DOWN - SDL_SCANCODE_RIGHT, // SHORTCUT_SCROLL_MAP_RIGHT - SDL_SCANCODE_C, // SHORTCUT_OPEN_CHAT_WINDOW - PLATFORM_MODIFIER | SDL_SCANCODE_F10, // SHORTCUT_QUICK_SAVE_GAME - - SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_OPTIONS - SHORTCUT_UNDEFINED, // SHORTCUT_MUTE_SOUND - ALT | SDL_SCANCODE_RETURN, // SHORTCUT_WINDOWED_MODE_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_MULTIPLAYER - SHORTCUT_UNDEFINED, // SHORTCUT_PAINT_ORIGINAL_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_DEBUG_PAINT_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_SEE_THROUGH_PATHS_TOGGLE -}; - -#define SHORTCUT_FILE_VERSION 1 - -/** - * - * rct2: 0x006E3604 - */ -void config_reset_shortcut_keys() -{ - memcpy(gShortcutKeys, _defaultShortcutKeys, sizeof(gShortcutKeys)); -} - -static void config_shortcut_keys_get_path(utf8 *outPath, size_t size) -{ - platform_get_user_directory(outPath, NULL, size); - safe_strcat_path(outPath, "hotkeys.cfg", size); -} - -bool config_shortcut_keys_load() -{ - utf8 path[MAX_PATH]; - SDL_RWops *file; - bool result; - uint16 version; - - config_shortcut_keys_get_path(path, sizeof(path)); - - file = SDL_RWFromFile(path, "rb"); - if (file != NULL) { - result = SDL_RWread(file, &version, sizeof(version), 1) == 1; - if (result && version == SHORTCUT_FILE_VERSION) { - for (sint32 i = 0; i < SHORTCUT_COUNT; i++) { - if (SDL_RWread(file, &gShortcutKeys[i], sizeof(uint16), 1) != 1) { - break; - } - } - } else { - result = false; - } - SDL_RWclose(file); - } else { - result = false; - } - - return result; -} - -bool config_shortcut_keys_save() -{ - const uint16 version = SHORTCUT_FILE_VERSION; - - utf8 path[MAX_PATH]; - SDL_RWops *file; - bool result; - - config_shortcut_keys_get_path(path, sizeof(path)); - - file = SDL_RWFromFile(path, "wb"); - if (file != NULL) { - result = SDL_RWwrite(file, &version, sizeof(version), 1) == 1; - if (result) { - result = SDL_RWwrite(file, gShortcutKeys, sizeof(gShortcutKeys), 1) == 1; - } - SDL_RWclose(file); - } else { - result = false; - } - - return result; -} - -#pragma endregion diff --git a/src/openrct2/config.h b/src/openrct2/config.h deleted file mode 100644 index 496ea118f1..0000000000 --- a/src/openrct2/config.h +++ /dev/null @@ -1,100 +0,0 @@ -#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers -/***************************************************************************** - * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. - * - * OpenRCT2 is the work of many authors, a full list can be found in contributors.md - * For more information, visit https://github.com/OpenRCT2/OpenRCT2 - * - * OpenRCT2 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. - * - * A full copy of the GNU General Public License can be found in licence.txt - *****************************************************************************/ -#pragma endregion - -#ifndef _CONFIG_H_ -#define _CONFIG_H_ - -#include "common.h" -#include "localisation/currency.h" -#include "platform/platform.h" - -enum { - SHORTCUT_CLOSE_TOP_MOST_WINDOW, - SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS, - SHORTCUT_CANCEL_CONSTRUCTION_MODE, - SHORTCUT_PAUSE_GAME, - SHORTCUT_ZOOM_VIEW_OUT, - SHORTCUT_ZOOM_VIEW_IN, - SHORTCUT_ROTATE_VIEW_CLOCKWISE, - SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE, - SHORTCUT_ROTATE_CONSTRUCTION_OBJECT, - SHORTCUT_UNDERGROUND_VIEW_TOGGLE, - SHORTCUT_REMOVE_BASE_LAND_TOGGLE, - SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE, - SHORTCUT_SEE_THROUGH_RIDES_TOGGLE, - SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE, - SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE, - SHORTCUT_INVISIBLE_PEOPLE_TOGGLE, - SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE, - SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE, - SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE, - SHORTCUT_ADJUST_LAND, - SHORTCUT_ADJUST_WATER, - SHORTCUT_BUILD_SCENERY, - SHORTCUT_BUILD_PATHS, - SHORTCUT_BUILD_NEW_RIDE, - SHORTCUT_SHOW_FINANCIAL_INFORMATION, - SHORTCUT_SHOW_RESEARCH_INFORMATION, - SHORTCUT_SHOW_RIDES_LIST, - SHORTCUT_SHOW_PARK_INFORMATION, - SHORTCUT_SHOW_GUEST_LIST, - SHORTCUT_SHOW_STAFF_LIST, - SHORTCUT_SHOW_RECENT_MESSAGES, - SHORTCUT_SHOW_MAP, - SHORTCUT_SCREENSHOT, - - // New - SHORTCUT_REDUCE_GAME_SPEED, - SHORTCUT_INCREASE_GAME_SPEED, - SHORTCUT_OPEN_CHEAT_WINDOW, - SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, - SHORTCUT_SCROLL_MAP_UP, - SHORTCUT_SCROLL_MAP_LEFT, - SHORTCUT_SCROLL_MAP_DOWN, - SHORTCUT_SCROLL_MAP_RIGHT, - SHORTCUT_OPEN_CHAT_WINDOW, - SHORTCUT_QUICK_SAVE_GAME, - SHORTCUT_SHOW_OPTIONS, - SHORTCUT_MUTE_SOUND, - SHORTCUT_WINDOWED_MODE_TOGGLE, - SHORTCUT_SHOW_MULTIPLAYER, - SHORTCUT_PAINT_ORIGINAL_TOGGLE, - SHORTCUT_DEBUG_PAINT_TOGGLE, - SHORTCUT_SEE_THROUGH_PATHS_TOGGLE, - - SHORTCUT_COUNT -}; - -typedef struct shortcut_entry { - uint8 key; - uint8 modifier; -} shortcut_entry; - -extern uint16 gShortcutKeys[SHORTCUT_COUNT]; - -void config_get_default_path(utf8 *outPath, size_t size); -void config_set_defaults(); -void config_release(); -bool config_open_default(); -bool config_save_default(); - -void config_reset_shortcut_keys(); -bool config_shortcut_keys_load(); -bool config_shortcut_keys_save(); - -bool config_find_or_browse_install_directory(); - -#endif diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index 4945802677..040042e599 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -220,4 +220,10 @@ extern "C" { bool config_open(const utf8 * path); bool config_save(const utf8 * path); + void config_get_default_path(utf8 *outPath, size_t size); + void config_set_defaults(); + void config_release(); + bool config_open_default(); + bool config_save_default(); + bool config_find_or_browse_install_directory(); } diff --git a/src/openrct2/config/KeyboardShortcuts.cpp b/src/openrct2/config/KeyboardShortcuts.cpp new file mode 100644 index 0000000000..95e0cdbd4e --- /dev/null +++ b/src/openrct2/config/KeyboardShortcuts.cpp @@ -0,0 +1,165 @@ +#pragma region Copyright (c) 2014-2016 OpenRCT2 Developers +/***************************************************************************** + * OpenRCT2, an open source clone of Roller Coaster Tycoon 2. + * + * OpenRCT2 is the work of many authors, a full list can be found in contributors.md + * For more information, visit https://github.com/OpenRCT2/OpenRCT2 + * + * OpenRCT2 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. + * + * A full copy of the GNU General Public License can be found in licence.txt + *****************************************************************************/ +#pragma endregion + +#include "../common.h" +#include "../core/Console.hpp" +#include "../core/FileStream.hpp" +#include "../core/Memory.hpp" +#include "../core/Path.hpp" +#include "../core/String.hpp" +#include "../interface/keyboard_shortcut.h" + +extern "C" +{ + #include "../platform/platform.h" +} + +// Current keyboard shortcuts +uint16 gShortcutKeys[SHORTCUT_COUNT]; + +namespace KeyboardShortcuts +{ + // Default keyboard shortcuts + static const uint16 _defaultShortcutKeys[SHORTCUT_COUNT] = + { + SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_TOP_MOST_WINDOW + SHIFT | SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS + SDL_SCANCODE_ESCAPE, // SHORTCUT_CANCEL_CONSTRUCTION_MODE + SDL_SCANCODE_PAUSE, // SHORTCUT_PAUSE_GAME + SDL_SCANCODE_PAGEUP, // SHORTCUT_ZOOM_VIEW_OUT + SDL_SCANCODE_PAGEDOWN, // SHORTCUT_ZOOM_VIEW_IN + SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_CLOCKWISE + SHIFT | SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE + SDL_SCANCODE_Z, // SHORTCUT_ROTATE_CONSTRUCTION_OBJECT + SDL_SCANCODE_1, // SHORTCUT_UNDERGROUND_VIEW_TOGGLE + SDL_SCANCODE_H, // SHORTCUT_REMOVE_BASE_LAND_TOGGLE + SDL_SCANCODE_V, // SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE + SDL_SCANCODE_3, // SHORTCUT_SEE_THROUGH_RIDES_TOGGLE + SDL_SCANCODE_4, // SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE + SDL_SCANCODE_5, // SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE + SDL_SCANCODE_6, // SHORTCUT_INVISIBLE_PEOPLE_TOGGLE + SDL_SCANCODE_8, // SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE + SDL_SCANCODE_9, // SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE + SDL_SCANCODE_0, // SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE + SDL_SCANCODE_F1, // SHORTCUT_ADJUST_LAND + SDL_SCANCODE_F2, // SHORTCUT_ADJUST_WATER + SDL_SCANCODE_F3, // SHORTCUT_BUILD_SCENERY + SDL_SCANCODE_F4, // SHORTCUT_BUILD_PATHS + SDL_SCANCODE_F5, // SHORTCUT_BUILD_NEW_RIDE + SDL_SCANCODE_F, // SHORTCUT_SHOW_FINANCIAL_INFORMATION + SDL_SCANCODE_D, // SHORTCUT_SHOW_RESEARCH_INFORMATION + SDL_SCANCODE_R, // SHORTCUT_SHOW_RIDES_LIST + SDL_SCANCODE_P, // SHORTCUT_SHOW_PARK_INFORMATION + SDL_SCANCODE_G, // SHORTCUT_SHOW_GUEST_LIST + SDL_SCANCODE_S, // SHORTCUT_SHOW_STAFF_LIST + SDL_SCANCODE_M, // SHORTCUT_SHOW_RECENT_MESSAGES + SDL_SCANCODE_TAB, // SHORTCUT_SHOW_MAP + PLATFORM_MODIFIER | SDL_SCANCODE_S, // SHORTCUT_SCREENSHOT + + // New + SDL_SCANCODE_MINUS, // SHORTCUT_REDUCE_GAME_SPEED, + SDL_SCANCODE_EQUALS, // SHORTCUT_INCREASE_GAME_SPEED, + PLATFORM_MODIFIER | ALT | SDL_SCANCODE_C, // SHORTCUT_OPEN_CHEAT_WINDOW, + SDL_SCANCODE_T, // SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, + SDL_SCANCODE_UP, // SHORTCUT_SCROLL_MAP_UP + SDL_SCANCODE_LEFT, // SHORTCUT_SCROLL_MAP_LEFT + SDL_SCANCODE_DOWN, // SHORTCUT_SCROLL_MAP_DOWN + SDL_SCANCODE_RIGHT, // SHORTCUT_SCROLL_MAP_RIGHT + SDL_SCANCODE_C, // SHORTCUT_OPEN_CHAT_WINDOW + PLATFORM_MODIFIER | SDL_SCANCODE_F10, // SHORTCUT_QUICK_SAVE_GAME + + SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_OPTIONS + SHORTCUT_UNDEFINED, // SHORTCUT_MUTE_SOUND + ALT | SDL_SCANCODE_RETURN, // SHORTCUT_WINDOWED_MODE_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_MULTIPLAYER + SHORTCUT_UNDEFINED, // SHORTCUT_PAINT_ORIGINAL_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_DEBUG_PAINT_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_SEE_THROUGH_PATHS_TOGGLE + }; + + constexpr sint32 CURRENT_FILE_VERSION = 1; + + static void Reset() + { + Memory::Copy(gShortcutKeys, _defaultShortcutKeys, sizeof(gShortcutKeys)); + } + + static std::string GetPath() + { + utf8 path[MAX_PATH]; + platform_get_user_directory(path, nullptr, sizeof(path)); + Path::Append(path, sizeof(path), "hotkeys.cfg"); + return path; + } +} + +extern "C" +{ + void config_reset_shortcut_keys() + { + KeyboardShortcuts::Reset(); + } + + bool config_shortcut_keys_load() + { + bool result = false; + try + { + std::string path = KeyboardShortcuts::GetPath(); + auto fs = FileStream(path, FILE_MODE_OPEN); + + uint16 version = fs.ReadValue(); + if (version == KeyboardShortcuts::CURRENT_FILE_VERSION) + { + for (sint32 i = 0; i < SHORTCUT_COUNT; i++) + { + gShortcutKeys[i] = fs.ReadValue(); + } + result = true; + } + else + { + result = false; + } + } + catch (const Exception &ex) + { + Console::WriteLine("Error reading shortcut keys: %s", ex.GetMessage()); + } + return result; + } + + bool config_shortcut_keys_save() + { + bool result = false; + try + { + std::string path = KeyboardShortcuts::GetPath(); + auto fs = FileStream(path, FILE_MODE_WRITE); + fs.WriteValue(KeyboardShortcuts::CURRENT_FILE_VERSION); + for (sint32 i = 0; i < SHORTCUT_COUNT; i++) + { + fs.WriteValue(gShortcutKeys[i]); + } + result = true; + } + catch (const Exception &ex) + { + Console::WriteLine("Error writing shortcut keys: %s", ex.GetMessage()); + } + return result; + } +} diff --git a/src/openrct2/interface/keyboard_shortcut.h b/src/openrct2/interface/keyboard_shortcut.h index 9e2c8fefc5..4d4efd24dc 100644 --- a/src/openrct2/interface/keyboard_shortcut.h +++ b/src/openrct2/interface/keyboard_shortcut.h @@ -29,4 +29,72 @@ void keyboard_shortcut_handle(sint32 key); void keyboard_shortcut_handle_command(sint32 shortcutIndex); void keyboard_shortcut_format_string(char *buffer, size_t size, uint16 shortcutKey); +void config_reset_shortcut_keys(); +bool config_shortcut_keys_load(); +bool config_shortcut_keys_save(); + +typedef struct shortcut_entry { + uint8 key; + uint8 modifier; +} shortcut_entry; + +extern uint16 gShortcutKeys[SHORTCUT_COUNT]; + +enum { + SHORTCUT_CLOSE_TOP_MOST_WINDOW, + SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS, + SHORTCUT_CANCEL_CONSTRUCTION_MODE, + SHORTCUT_PAUSE_GAME, + SHORTCUT_ZOOM_VIEW_OUT, + SHORTCUT_ZOOM_VIEW_IN, + SHORTCUT_ROTATE_VIEW_CLOCKWISE, + SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE, + SHORTCUT_ROTATE_CONSTRUCTION_OBJECT, + SHORTCUT_UNDERGROUND_VIEW_TOGGLE, + SHORTCUT_REMOVE_BASE_LAND_TOGGLE, + SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE, + SHORTCUT_SEE_THROUGH_RIDES_TOGGLE, + SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE, + SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE, + SHORTCUT_INVISIBLE_PEOPLE_TOGGLE, + SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE, + SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE, + SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE, + SHORTCUT_ADJUST_LAND, + SHORTCUT_ADJUST_WATER, + SHORTCUT_BUILD_SCENERY, + SHORTCUT_BUILD_PATHS, + SHORTCUT_BUILD_NEW_RIDE, + SHORTCUT_SHOW_FINANCIAL_INFORMATION, + SHORTCUT_SHOW_RESEARCH_INFORMATION, + SHORTCUT_SHOW_RIDES_LIST, + SHORTCUT_SHOW_PARK_INFORMATION, + SHORTCUT_SHOW_GUEST_LIST, + SHORTCUT_SHOW_STAFF_LIST, + SHORTCUT_SHOW_RECENT_MESSAGES, + SHORTCUT_SHOW_MAP, + SHORTCUT_SCREENSHOT, + + // New + SHORTCUT_REDUCE_GAME_SPEED, + SHORTCUT_INCREASE_GAME_SPEED, + SHORTCUT_OPEN_CHEAT_WINDOW, + SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, + SHORTCUT_SCROLL_MAP_UP, + SHORTCUT_SCROLL_MAP_LEFT, + SHORTCUT_SCROLL_MAP_DOWN, + SHORTCUT_SCROLL_MAP_RIGHT, + SHORTCUT_OPEN_CHAT_WINDOW, + SHORTCUT_QUICK_SAVE_GAME, + SHORTCUT_SHOW_OPTIONS, + SHORTCUT_MUTE_SOUND, + SHORTCUT_WINDOWED_MODE_TOGGLE, + SHORTCUT_SHOW_MULTIPLAYER, + SHORTCUT_PAINT_ORIGINAL_TOGGLE, + SHORTCUT_DEBUG_PAINT_TOGGLE, + SHORTCUT_SEE_THROUGH_PATHS_TOGGLE, + + SHORTCUT_COUNT +}; + #endif diff --git a/src/openrct2/libopenrct2.vcxproj b/src/openrct2/libopenrct2.vcxproj index 689c958415..e16cd20dc9 100644 --- a/src/openrct2/libopenrct2.vcxproj +++ b/src/openrct2/libopenrct2.vcxproj @@ -75,6 +75,7 @@ + @@ -91,7 +92,6 @@ - @@ -440,7 +440,6 @@ - From fb2c835d527838c5e04a477af8542d411312e3ef Mon Sep 17 00:00:00 2001 From: Ted John Date: Sat, 18 Feb 2017 15:45:10 +0000 Subject: [PATCH 16/50] Include new config header --- src/openrct2/OpenRCT2.cpp | 2 +- src/openrct2/audio/AudioMixer.cpp | 2 +- src/openrct2/audio/audio.cpp | 2 +- src/openrct2/cheats.c | 2 +- src/openrct2/cmdline/RootCommands.cpp | 2 +- src/openrct2/config/Config.cpp | 9 +++++ src/openrct2/config/Config.h | 20 ++++++----- src/openrct2/config/KeyboardShortcuts.cpp | 2 +- src/openrct2/drawing/IDrawingEngine.h | 10 ++++-- src/openrct2/drawing/NewDrawing.cpp | 2 +- src/openrct2/drawing/Rain.cpp | 2 +- .../drawing/engines/SoftwareDrawingEngine.cpp | 2 +- .../engines/opengl/OpenGLDrawingEngine.cpp | 4 +-- src/openrct2/drawing/scrolling_text.c | 2 +- src/openrct2/drawing/sprite.cpp | 2 +- src/openrct2/drawing/string.c | 1 + src/openrct2/game.c | 2 +- src/openrct2/input.c | 2 +- src/openrct2/interface/Fonts.cpp | 2 +- src/openrct2/interface/Theme.cpp | 3 +- src/openrct2/interface/console.c | 2 +- src/openrct2/interface/keyboard_shortcut.c | 2 +- src/openrct2/interface/keyboard_shortcut.h | 4 +-- src/openrct2/interface/screenshot.c | 2 +- src/openrct2/interface/viewport.c | 2 +- src/openrct2/interface/window.c | 2 +- src/openrct2/localisation/currency.c | 2 +- src/openrct2/localisation/localisation.c | 2 +- src/openrct2/management/award.c | 2 +- src/openrct2/management/marketing.c | 2 +- src/openrct2/management/research.c | 2 +- .../network/NetworkServerAdvertiser.cpp | 2 +- src/openrct2/network/network.cpp | 2 +- src/openrct2/network/twitch.cpp | 2 +- src/openrct2/object/ObjectRepository.cpp | 2 +- src/openrct2/object/RideObject.cpp | 2 +- src/openrct2/paint/map_element/banner.c | 2 +- src/openrct2/paint/map_element/entrance.c | 2 +- src/openrct2/paint/map_element/fence.c | 2 +- src/openrct2/paint/map_element/map_element.c | 2 +- src/openrct2/paint/map_element/path.c | 2 +- src/openrct2/paint/map_element/scenery.c | 2 +- .../paint/map_element/scenery_multiple.c | 2 +- src/openrct2/paint/map_element/surface.c | 2 +- src/openrct2/paint/paint.c | 2 +- src/openrct2/paint/sprite/peep.c | 2 +- src/openrct2/peep/peep.c | 2 +- src/openrct2/peep/staff.c | 2 +- src/openrct2/platform/linux.c | 2 +- src/openrct2/platform/posix.c | 2 +- src/openrct2/platform/shared.c | 3 +- src/openrct2/platform/windows.c | 2 +- src/openrct2/rct1.c | 2 +- src/openrct2/rct2.c | 3 +- src/openrct2/rct2/S6Exporter.cpp | 2 +- src/openrct2/rct2/S6Importer.cpp | 2 +- src/openrct2/ride/gentle/mini_golf.c | 2 +- src/openrct2/ride/ride.c | 2 +- src/openrct2/ride/thrill/launched_freefall.c | 2 +- src/openrct2/ride/track.c | 2 +- src/openrct2/ride/track_design_save.c | 2 +- src/openrct2/ride/track_paint.c | 2 +- src/openrct2/ride/vehicle.c | 2 +- src/openrct2/ride/water/river_rapids.c | 2 +- src/openrct2/ride/water/splash_boats.c | 2 +- src/openrct2/scenario/ScenarioRepository.cpp | 3 +- src/openrct2/scenario/scenario.c | 2 +- src/openrct2/scenario/scenario.h | 3 +- src/openrct2/title/TitleScreen.cpp | 2 +- src/openrct2/windows/banner.c | 2 +- src/openrct2/windows/cheats.c | 2 +- src/openrct2/windows/custom_currency.c | 2 +- src/openrct2/windows/editor_bottom_toolbar.c | 2 +- .../windows/editor_object_selection.c | 2 +- src/openrct2/windows/error.c | 3 +- src/openrct2/windows/finances.c | 2 +- src/openrct2/windows/game_bottom_toolbar.c | 2 +- src/openrct2/windows/guest.c | 2 +- src/openrct2/windows/guest_list.c | 2 +- src/openrct2/windows/install_track.c | 3 +- src/openrct2/windows/loadsave.c | 2 +- src/openrct2/windows/map_tooltip.c | 3 +- src/openrct2/windows/multiplayer.c | 2 +- src/openrct2/windows/new_campaign.c | 2 +- src/openrct2/windows/new_ride.c | 2 +- src/openrct2/windows/news_options.c | 36 +++++++++---------- src/openrct2/windows/options.c | 3 +- src/openrct2/windows/park.c | 2 +- src/openrct2/windows/player.c | 2 +- src/openrct2/windows/ride.c | 2 +- src/openrct2/windows/ride_construction.c | 2 +- src/openrct2/windows/ride_list.c | 2 +- src/openrct2/windows/save_prompt.c | 2 +- src/openrct2/windows/server_list.c | 2 +- src/openrct2/windows/server_start.c | 2 +- src/openrct2/windows/shortcut_key_change.c | 2 +- src/openrct2/windows/shortcut_keys.c | 2 +- src/openrct2/windows/sign.c | 2 +- src/openrct2/windows/staff.c | 2 +- src/openrct2/windows/staff_list.c | 2 +- src/openrct2/windows/text_input.c | 2 +- src/openrct2/windows/themes.c | 2 +- src/openrct2/windows/title_editor.c | 2 +- src/openrct2/windows/title_exit.c | 2 +- src/openrct2/windows/title_menu.c | 2 +- src/openrct2/windows/title_options.c | 2 +- src/openrct2/windows/title_scenarioselect.c | 2 +- src/openrct2/windows/top_toolbar.c | 2 +- src/openrct2/windows/track_list.c | 3 +- src/openrct2/windows/view_clipping.c | 2 +- src/openrct2/world/climate.c | 2 +- src/openrct2/world/map.c | 2 +- src/openrct2/world/park.c | 2 +- 113 files changed, 166 insertions(+), 140 deletions(-) diff --git a/src/openrct2/OpenRCT2.cpp b/src/openrct2/OpenRCT2.cpp index 72fbb8d749..9de2e9cf6f 100644 --- a/src/openrct2/OpenRCT2.cpp +++ b/src/openrct2/OpenRCT2.cpp @@ -35,7 +35,7 @@ extern "C" { #include "audio/audio.h" - #include "config.h" + #include "config/Config.h" #include "editor.h" #include "game.h" #include "interface/chat.h" diff --git a/src/openrct2/audio/AudioMixer.cpp b/src/openrct2/audio/AudioMixer.cpp index 981d45c0ed..af0a2e6370 100644 --- a/src/openrct2/audio/AudioMixer.cpp +++ b/src/openrct2/audio/AudioMixer.cpp @@ -25,7 +25,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../localisation/localisation.h" #include "../OpenRCT2.h" #include "../platform/platform.h" diff --git a/src/openrct2/audio/audio.cpp b/src/openrct2/audio/audio.cpp index b4d83e54f7..d5efc2cabd 100644 --- a/src/openrct2/audio/audio.cpp +++ b/src/openrct2/audio/audio.cpp @@ -24,7 +24,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../interface/viewport.h" #include "../intro.h" #include "../localisation/language.h" diff --git a/src/openrct2/cheats.c b/src/openrct2/cheats.c index 48ec7a62f9..bdf2bf7b5a 100644 --- a/src/openrct2/cheats.c +++ b/src/openrct2/cheats.c @@ -15,7 +15,7 @@ #pragma endregion #include "cheats.h" -#include "config.h" +#include "config/Config.h" #include "game.h" #include "interface/window.h" #include "localisation/date.h" diff --git a/src/openrct2/cmdline/RootCommands.cpp b/src/openrct2/cmdline/RootCommands.cpp index 62fb60ffb3..b68ca8e7f1 100644 --- a/src/openrct2/cmdline/RootCommands.cpp +++ b/src/openrct2/cmdline/RootCommands.cpp @@ -20,7 +20,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../platform/crash.h" } diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 0ba2d67294..50d1e4917e 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -33,6 +33,7 @@ extern "C" #include "../localisation/currency.h" #include "../localisation/date.h" #include "../localisation/language.h" + #include "../platform/platform.h" #include "../scenario/scenario.h" } @@ -587,6 +588,14 @@ namespace Config extern "C" { + GeneralConfiguration gConfigGeneral; + InterfaceConfiguration gConfigInterface; + SoundConfiguration gConfigSound; + TwitchConfiguration gConfigTwitch; + NetworkConfiguration gConfigNetwork; + NotificationConfiguration gConfigNotifications; + FontConfiguration gConfigFonts; + void config_set_defaults() { Config::SetDefaults(); diff --git a/src/openrct2/config/Config.h b/src/openrct2/config/Config.h index 040042e599..d8f812666a 100644 --- a/src/openrct2/config/Config.h +++ b/src/openrct2/config/Config.h @@ -187,14 +187,6 @@ typedef struct FontConfiguration sint32 height_big; } FontConfiguration; -extern GeneralConfiguration gConfigGeneral; -extern InterfaceConfiguration gConfigInterface; -extern SoundConfiguration gConfigSound; -extern TwitchConfiguration gConfigTwitch; -extern NetworkConfiguration gConfigNetwork; -extern NotificationConfiguration gConfigNotifications; -extern FontConfiguration gConfigFonts; - enum SORT { SORT_NAME_ASCENDING, @@ -216,8 +208,18 @@ enum MEASUREMENT_FORMAT MEASUREMENT_FORMAT_SI }; +#ifdef __cplusplus extern "C" { +#endif + extern GeneralConfiguration gConfigGeneral; + extern InterfaceConfiguration gConfigInterface; + extern SoundConfiguration gConfigSound; + extern TwitchConfiguration gConfigTwitch; + extern NetworkConfiguration gConfigNetwork; + extern NotificationConfiguration gConfigNotifications; + extern FontConfiguration gConfigFonts; + bool config_open(const utf8 * path); bool config_save(const utf8 * path); void config_get_default_path(utf8 *outPath, size_t size); @@ -226,4 +228,6 @@ extern "C" bool config_open_default(); bool config_save_default(); bool config_find_or_browse_install_directory(); +#ifdef __cplusplus } +#endif diff --git a/src/openrct2/config/KeyboardShortcuts.cpp b/src/openrct2/config/KeyboardShortcuts.cpp index 95e0cdbd4e..e2b9272188 100644 --- a/src/openrct2/config/KeyboardShortcuts.cpp +++ b/src/openrct2/config/KeyboardShortcuts.cpp @@ -20,10 +20,10 @@ #include "../core/Memory.hpp" #include "../core/Path.hpp" #include "../core/String.hpp" -#include "../interface/keyboard_shortcut.h" extern "C" { + #include "../interface/keyboard_shortcut.h" #include "../platform/platform.h" } diff --git a/src/openrct2/drawing/IDrawingEngine.h b/src/openrct2/drawing/IDrawingEngine.h index 96cb70b387..a9e7287201 100644 --- a/src/openrct2/drawing/IDrawingEngine.h +++ b/src/openrct2/drawing/IDrawingEngine.h @@ -20,9 +20,6 @@ #include -struct rct_drawpixelinfo; -interface IDrawingContext; - enum DRAWING_ENGINE { DRAWING_ENGINE_NONE = -1, @@ -41,6 +38,11 @@ enum DRAWING_ENGINE_FLAGS DEF_DIRTY_OPTIMISATIONS = 1 << 0, }; +#ifdef __cplusplus + +struct rct_drawpixelinfo; +interface IDrawingContext; + interface IDrawingEngine { virtual ~IDrawingEngine() { } @@ -81,3 +83,5 @@ interface IRainDrawer sint32 xStart, sint32 yStart) abstract; }; + +#endif diff --git a/src/openrct2/drawing/NewDrawing.cpp b/src/openrct2/drawing/NewDrawing.cpp index 1b91c5dcca..5e2b479ad8 100644 --- a/src/openrct2/drawing/NewDrawing.cpp +++ b/src/openrct2/drawing/NewDrawing.cpp @@ -21,7 +21,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../drawing/drawing.h" #include "../interface/screenshot.h" #include "../localisation/string_ids.h" diff --git a/src/openrct2/drawing/Rain.cpp b/src/openrct2/drawing/Rain.cpp index b73e64ed43..5cf27f7ef7 100644 --- a/src/openrct2/drawing/Rain.cpp +++ b/src/openrct2/drawing/Rain.cpp @@ -19,7 +19,7 @@ extern "C" #include "../interface/window.h" #include "../world/climate.h" #include "drawing.h" - #include "../config.h" + #include "../config/Config.h" } #include "IDrawingEngine.h" diff --git a/src/openrct2/drawing/engines/SoftwareDrawingEngine.cpp b/src/openrct2/drawing/engines/SoftwareDrawingEngine.cpp index a1a6a14f8e..87ab3a7459 100644 --- a/src/openrct2/drawing/engines/SoftwareDrawingEngine.cpp +++ b/src/openrct2/drawing/engines/SoftwareDrawingEngine.cpp @@ -23,7 +23,7 @@ extern "C" { - #include "../../config.h" + #include "../../config/Config.h" #include "../../game.h" #include "../../interface/screenshot.h" #include "../../interface/viewport.h" diff --git a/src/openrct2/drawing/engines/opengl/OpenGLDrawingEngine.cpp b/src/openrct2/drawing/engines/opengl/OpenGLDrawingEngine.cpp index 725f484428..e870cf540b 100644 --- a/src/openrct2/drawing/engines/opengl/OpenGLDrawingEngine.cpp +++ b/src/openrct2/drawing/engines/opengl/OpenGLDrawingEngine.cpp @@ -47,11 +47,11 @@ IDrawingEngine * DrawingEngineFactory::CreateOpenGL() #include "../../IDrawingContext.h" #include "../../IDrawingEngine.h" #include "../../Rain.h" -#include "../../../config.h" +#include "../../../config/Config.h" extern "C" { - #include "../../../config.h" + #include "../../../config/Config.h" #include "../../../interface/screenshot.h" #include "../../../interface/window.h" #include "../../../intro.h" diff --git a/src/openrct2/drawing/scrolling_text.c b/src/openrct2/drawing/scrolling_text.c index 3334f6f2cb..746b8fd6ad 100644 --- a/src/openrct2/drawing/scrolling_text.c +++ b/src/openrct2/drawing/scrolling_text.c @@ -15,7 +15,7 @@ #pragma endregion #include "../rct2/addresses.h" -#include "../config.h" +#include "../config/Config.h" #include "../interface/colour.h" #include "../localisation/localisation.h" #include "../sprites.h" diff --git a/src/openrct2/drawing/sprite.cpp b/src/openrct2/drawing/sprite.cpp index 1a27f690dc..f58c1752ad 100644 --- a/src/openrct2/drawing/sprite.cpp +++ b/src/openrct2/drawing/sprite.cpp @@ -24,7 +24,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../rct2/addresses.h" #include "../util/util.h" #include "drawing.h" diff --git a/src/openrct2/drawing/string.c b/src/openrct2/drawing/string.c index 7733a39ca6..621897b7f3 100644 --- a/src/openrct2/drawing/string.c +++ b/src/openrct2/drawing/string.c @@ -17,6 +17,7 @@ #include "../interface/colour.h" #include "../interface/viewport.h" #include "../localisation/localisation.h" +#include "../platform/platform.h" #include "../sprites.h" #include "../util/util.h" diff --git a/src/openrct2/game.c b/src/openrct2/game.c index 43fa7e97a1..f42a5771b9 100644 --- a/src/openrct2/game.c +++ b/src/openrct2/game.c @@ -16,7 +16,7 @@ #include "audio/audio.h" #include "cheats.h" -#include "config.h" +#include "config/Config.h" #include "editor.h" #include "game.h" #include "input.h" diff --git a/src/openrct2/input.c b/src/openrct2/input.c index 39284a33b7..7c693b92d5 100644 --- a/src/openrct2/input.c +++ b/src/openrct2/input.c @@ -16,7 +16,7 @@ #include #include "audio/audio.h" -#include "config.h" +#include "config/Config.h" #include "game.h" #include "input.h" #include "interface/chat.h" diff --git a/src/openrct2/interface/Fonts.cpp b/src/openrct2/interface/Fonts.cpp index 66fad11583..ca6d759703 100644 --- a/src/openrct2/interface/Fonts.cpp +++ b/src/openrct2/interface/Fonts.cpp @@ -21,7 +21,7 @@ #include "Fonts.h" extern "C" { -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../localisation/language.h" } diff --git a/src/openrct2/interface/Theme.cpp b/src/openrct2/interface/Theme.cpp index 4c419ce5f8..ff0cb0fc86 100644 --- a/src/openrct2/interface/Theme.cpp +++ b/src/openrct2/interface/Theme.cpp @@ -22,7 +22,8 @@ extern "C" { #include "../common.h" - #include "../config.h" + #include "../config/Config.h" + #include "../platform/platform.h" #include "themes.h" #include "window.h" } diff --git a/src/openrct2/interface/console.c b/src/openrct2/interface/console.c index bd3aeedec7..488cdd0228 100644 --- a/src/openrct2/interface/console.c +++ b/src/openrct2/interface/console.c @@ -17,7 +17,7 @@ #include #include -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/interface/keyboard_shortcut.c b/src/openrct2/interface/keyboard_shortcut.c index 23d21021b1..ff561361bb 100644 --- a/src/openrct2/interface/keyboard_shortcut.c +++ b/src/openrct2/interface/keyboard_shortcut.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/interface/keyboard_shortcut.h b/src/openrct2/interface/keyboard_shortcut.h index 4d4efd24dc..29bf930c8f 100644 --- a/src/openrct2/interface/keyboard_shortcut.h +++ b/src/openrct2/interface/keyboard_shortcut.h @@ -38,8 +38,6 @@ typedef struct shortcut_entry { uint8 modifier; } shortcut_entry; -extern uint16 gShortcutKeys[SHORTCUT_COUNT]; - enum { SHORTCUT_CLOSE_TOP_MOST_WINDOW, SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS, @@ -97,4 +95,6 @@ enum { SHORTCUT_COUNT }; +extern uint16 gShortcutKeys[SHORTCUT_COUNT]; + #endif diff --git a/src/openrct2/interface/screenshot.c b/src/openrct2/interface/screenshot.c index 86a3f6af82..af45a9c394 100644 --- a/src/openrct2/interface/screenshot.c +++ b/src/openrct2/interface/screenshot.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../Imaging.h" diff --git a/src/openrct2/interface/viewport.c b/src/openrct2/interface/viewport.c index c48b043186..5dbe953783 100644 --- a/src/openrct2/interface/viewport.c +++ b/src/openrct2/interface/viewport.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/interface/window.c b/src/openrct2/interface/window.c index 39eec54670..6bcf417546 100644 --- a/src/openrct2/interface/window.c +++ b/src/openrct2/interface/window.c @@ -29,7 +29,7 @@ #include "viewport.h" #include "widget.h" #include "window.h" -#include "../config.h" +#include "../config/Config.h" #define RCT2_FIRST_WINDOW (g_window_list) #define RCT2_LAST_WINDOW (gWindowNextSlot - 1) diff --git a/src/openrct2/localisation/currency.c b/src/openrct2/localisation/currency.c index aa570ebc23..2081cb2085 100644 --- a/src/openrct2/localisation/currency.c +++ b/src/openrct2/localisation/currency.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../util/util.h" #include "currency.h" #include "string_ids.h" diff --git a/src/openrct2/localisation/localisation.c b/src/openrct2/localisation/localisation.c index 6abd04d044..3bfb088cbb 100644 --- a/src/openrct2/localisation/localisation.c +++ b/src/openrct2/localisation/localisation.c @@ -23,7 +23,7 @@ #include #endif // __WINDOWS__ -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../util/util.h" #include "date.h" diff --git a/src/openrct2/management/award.c b/src/openrct2/management/award.c index df0b6982ed..f434d6e6d7 100644 --- a/src/openrct2/management/award.c +++ b/src/openrct2/management/award.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/window.h" #include "../localisation/localisation.h" #include "../peep/peep.h" diff --git a/src/openrct2/management/marketing.c b/src/openrct2/management/marketing.c index 3c0de6ff2d..0bcad0cb14 100644 --- a/src/openrct2/management/marketing.c +++ b/src/openrct2/management/marketing.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/window.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/management/research.c b/src/openrct2/management/research.c index e27835eb8e..8adf4d9d56 100644 --- a/src/openrct2/management/research.c +++ b/src/openrct2/management/research.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/window.h" #include "../localisation/date.h" diff --git a/src/openrct2/network/NetworkServerAdvertiser.cpp b/src/openrct2/network/NetworkServerAdvertiser.cpp index 194c108019..13b02df084 100644 --- a/src/openrct2/network/NetworkServerAdvertiser.cpp +++ b/src/openrct2/network/NetworkServerAdvertiser.cpp @@ -25,7 +25,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../localisation/date.h" #include "../management/finance.h" #include "../peep/peep.h" diff --git a/src/openrct2/network/network.cpp b/src/openrct2/network/network.cpp index 5126514345..ce8ef1a5a9 100644 --- a/src/openrct2/network/network.cpp +++ b/src/openrct2/network/network.cpp @@ -51,7 +51,7 @@ sint32 _pickup_peep_old_x = SPRITE_LOCATION_NULL; #include "../rct2/S6Exporter.h" extern "C" { -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/chat.h" #include "../interface/window.h" diff --git a/src/openrct2/network/twitch.cpp b/src/openrct2/network/twitch.cpp index 3ddf3e5a4a..7290a1640a 100644 --- a/src/openrct2/network/twitch.cpp +++ b/src/openrct2/network/twitch.cpp @@ -35,7 +35,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../interface/console.h" diff --git a/src/openrct2/object/ObjectRepository.cpp b/src/openrct2/object/ObjectRepository.cpp index a089805fce..9ffe6f038b 100644 --- a/src/openrct2/object/ObjectRepository.cpp +++ b/src/openrct2/object/ObjectRepository.cpp @@ -43,7 +43,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../localisation/localisation.h" #include "../object.h" #include "../object_list.h" diff --git a/src/openrct2/object/RideObject.cpp b/src/openrct2/object/RideObject.cpp index b1034c008c..476e452b76 100644 --- a/src/openrct2/object/RideObject.cpp +++ b/src/openrct2/object/RideObject.cpp @@ -23,7 +23,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../drawing/drawing.h" #include "../localisation/localisation.h" #include "../rct1.h" diff --git a/src/openrct2/paint/map_element/banner.c b/src/openrct2/paint/map_element/banner.c index 73dcc271aa..ccfcd33af9 100644 --- a/src/openrct2/paint/map_element/banner.c +++ b/src/openrct2/paint/map_element/banner.c @@ -15,7 +15,7 @@ #pragma endregion #include "../paint.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../game.h" #include "../../interface/viewport.h" #include "../../localisation/localisation.h" diff --git a/src/openrct2/paint/map_element/entrance.c b/src/openrct2/paint/map_element/entrance.c index 19d7156275..9f24b28ff2 100644 --- a/src/openrct2/paint/map_element/entrance.c +++ b/src/openrct2/paint/map_element/entrance.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../game.h" #include "../../interface/viewport.h" #include "../../localisation/localisation.h" diff --git a/src/openrct2/paint/map_element/fence.c b/src/openrct2/paint/map_element/fence.c index e7f8a1dc1d..362b97c96e 100644 --- a/src/openrct2/paint/map_element/fence.c +++ b/src/openrct2/paint/map_element/fence.c @@ -20,7 +20,7 @@ #include "../../world/scenery.h" #include "../../game.h" #include "../../ride/track.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../localisation/localisation.h" #include "../../interface/colour.h" #include "../../interface/viewport.h" diff --git a/src/openrct2/paint/map_element/map_element.c b/src/openrct2/paint/map_element/map_element.c index 1b0e748d1e..652e2acbab 100644 --- a/src/openrct2/paint/map_element/map_element.c +++ b/src/openrct2/paint/map_element/map_element.c @@ -21,7 +21,7 @@ #include "../../ride/ride_data.h" #include "../../ride/track_data.h" #include "../../ride/track_paint.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../world/sprite.h" #include "../../world/banner.h" #include "../../world/entrance.h" diff --git a/src/openrct2/paint/map_element/path.c b/src/openrct2/paint/map_element/path.c index 89e8c5038c..c2aeab96ed 100644 --- a/src/openrct2/paint/map_element/path.c +++ b/src/openrct2/paint/map_element/path.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../game.h" #include "../../interface/viewport.h" #include "../../localisation/localisation.h" diff --git a/src/openrct2/paint/map_element/scenery.c b/src/openrct2/paint/map_element/scenery.c index a6ba6c7304..165821a3ee 100644 --- a/src/openrct2/paint/map_element/scenery.c +++ b/src/openrct2/paint/map_element/scenery.c @@ -15,7 +15,7 @@ #pragma endregion #include "map_element.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../game.h" #include "../../interface/viewport.h" #include "../../localisation/date.h" diff --git a/src/openrct2/paint/map_element/scenery_multiple.c b/src/openrct2/paint/map_element/scenery_multiple.c index c0e9b64ec3..2f83176796 100644 --- a/src/openrct2/paint/map_element/scenery_multiple.c +++ b/src/openrct2/paint/map_element/scenery_multiple.c @@ -17,7 +17,7 @@ #include "map_element.h" #include "../paint.h" #include "../supports.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../game.h" #include "../../interface/viewport.h" #include "../../localisation/localisation.h" diff --git a/src/openrct2/paint/map_element/surface.c b/src/openrct2/paint/map_element/surface.c index 1b430f5807..5e422fdc12 100644 --- a/src/openrct2/paint/map_element/surface.c +++ b/src/openrct2/paint/map_element/surface.c @@ -15,7 +15,7 @@ #pragma endregion #include "../../cheats.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../interface/viewport.h" #include "../../peep/staff.h" #include "../../rct2.h" diff --git a/src/openrct2/paint/paint.c b/src/openrct2/paint/paint.c index 95121d63ca..c426510142 100644 --- a/src/openrct2/paint/paint.c +++ b/src/openrct2/paint/paint.c @@ -17,7 +17,7 @@ #include "paint.h" #include "../drawing/drawing.h" #include "../localisation/localisation.h" -#include "../config.h" +#include "../config/Config.h" #include "../interface/viewport.h" #include "map_element/map_element.h" #include "sprite/sprite.h" diff --git a/src/openrct2/paint/sprite/peep.c b/src/openrct2/paint/sprite/peep.c index 2baec97009..78629cb7b7 100644 --- a/src/openrct2/paint/sprite/peep.c +++ b/src/openrct2/paint/sprite/peep.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../drawing/lightfx.h" #include "../../interface/viewport.h" #include "../../paint/sprite/sprite.h" diff --git a/src/openrct2/peep/peep.c b/src/openrct2/peep/peep.c index aeef199b52..015e93bd90 100644 --- a/src/openrct2/peep/peep.c +++ b/src/openrct2/peep/peep.c @@ -17,7 +17,7 @@ #include "../audio/audio.h" #include "../audio/AudioMixer.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../input.h" #include "../interface/window.h" diff --git a/src/openrct2/peep/staff.c b/src/openrct2/peep/staff.c index d197541e21..fffb4c932e 100644 --- a/src/openrct2/peep/staff.c +++ b/src/openrct2/peep/staff.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../localisation/date.h" diff --git a/src/openrct2/platform/linux.c b/src/openrct2/platform/linux.c index 4805814fc3..252232f9a2 100644 --- a/src/openrct2/platform/linux.c +++ b/src/openrct2/platform/linux.c @@ -33,7 +33,7 @@ #include #include -#include "../config.h" +#include "../config/Config.h" #include "../localisation/language.h" #include "../localisation/string_ids.h" #include "../util/util.h" diff --git a/src/openrct2/platform/posix.c b/src/openrct2/platform/posix.c index e3c1a14a0c..10edddbf22 100644 --- a/src/openrct2/platform/posix.c +++ b/src/openrct2/platform/posix.c @@ -26,7 +26,7 @@ #include #include #include -#include "../config.h" +#include "../config/Config.h" #include "../localisation/language.h" #include "../OpenRCT2.h" #include "../util/util.h" diff --git a/src/openrct2/platform/shared.c b/src/openrct2/platform/shared.c index 69167de298..85904494fe 100644 --- a/src/openrct2/platform/shared.c +++ b/src/openrct2/platform/shared.c @@ -16,8 +16,9 @@ #include "../audio/audio.h" #include "../audio/AudioMixer.h" -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" +#include "../drawing/IDrawingEngine.h" #include "../drawing/lightfx.h" #include "../editor.h" #include "../game.h" diff --git a/src/openrct2/platform/windows.c b/src/openrct2/platform/windows.c index d7b4f944fe..6af069d80f 100644 --- a/src/openrct2/platform/windows.c +++ b/src/openrct2/platform/windows.c @@ -31,7 +31,7 @@ #include #include -#include "../config.h" +#include "../config/Config.h" #include "../localisation/language.h" #include "../OpenRCT2.h" #include "../util/util.h" diff --git a/src/openrct2/rct1.c b/src/openrct2/rct1.c index 087dbfc049..8fc3ec223f 100644 --- a/src/openrct2/rct1.c +++ b/src/openrct2/rct1.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "config.h" +#include "config/Config.h" #include "game.h" #include "localisation/string_ids.h" #include "rct1.h" diff --git a/src/openrct2/rct2.c b/src/openrct2/rct2.c index 0d060e2f1f..193b190f7f 100644 --- a/src/openrct2/rct2.c +++ b/src/openrct2/rct2.c @@ -19,7 +19,7 @@ #include #include "audio/audio.h" #include "audio/AudioMixer.h" -#include "config.h" +#include "config/Config.h" #include "drawing/drawing.h" #include "drawing/lightfx.h" #include "editor.h" @@ -27,6 +27,7 @@ #include "input.h" #include "interface/chat.h" #include "interface/console.h" +#include "interface/keyboard_shortcut.h" #include "interface/viewport.h" #include "intro.h" #include "localisation/date.h" diff --git a/src/openrct2/rct2/S6Exporter.cpp b/src/openrct2/rct2/S6Exporter.cpp index 4b021e594c..3a9e2c5d6a 100644 --- a/src/openrct2/rct2/S6Exporter.cpp +++ b/src/openrct2/rct2/S6Exporter.cpp @@ -27,7 +27,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../interface/window.h" diff --git a/src/openrct2/rct2/S6Importer.cpp b/src/openrct2/rct2/S6Importer.cpp index f235c4bb1e..63ab974b46 100644 --- a/src/openrct2/rct2/S6Importer.cpp +++ b/src/openrct2/rct2/S6Importer.cpp @@ -29,7 +29,7 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../localisation/date.h" diff --git a/src/openrct2/ride/gentle/mini_golf.c b/src/openrct2/ride/gentle/mini_golf.c index 85d097e713..fe4f327247 100644 --- a/src/openrct2/ride/gentle/mini_golf.c +++ b/src/openrct2/ride/gentle/mini_golf.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../interface/viewport.h" #include "../../paint/paint.h" #include "../../paint/supports.h" diff --git a/src/openrct2/ride/ride.c b/src/openrct2/ride/ride.c index 4bf2218982..db6155797a 100644 --- a/src/openrct2/ride/ride.c +++ b/src/openrct2/ride/ride.c @@ -18,7 +18,7 @@ #include "../audio/AudioMixer.h" #include "../cheats.h" #include "../common.h" -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/ride/thrill/launched_freefall.c b/src/openrct2/ride/thrill/launched_freefall.c index 9d05dc9e5f..0afca53064 100644 --- a/src/openrct2/ride/thrill/launched_freefall.c +++ b/src/openrct2/ride/thrill/launched_freefall.c @@ -15,7 +15,7 @@ #pragma endregion #include "../../common.h" -#include "../../config.h" +#include "../../config/Config.h" #include "../../interface/viewport.h" #include "../../world/sprite.h" #include "../../paint/paint.h" diff --git a/src/openrct2/ride/track.c b/src/openrct2/ride/track.c index 855a2a4bff..cfb7df9cfb 100644 --- a/src/openrct2/ride/track.c +++ b/src/openrct2/ride/track.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/ride/track_design_save.c b/src/openrct2/ride/track_design_save.c index 0066e2b4a0..504c801b21 100644 --- a/src/openrct2/ride/track_design_save.c +++ b/src/openrct2/ride/track_design_save.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../localisation/localisation.h" #include "../localisation/string_ids.h" diff --git a/src/openrct2/ride/track_paint.c b/src/openrct2/ride/track_paint.c index d157556aad..be45d6b807 100644 --- a/src/openrct2/ride/track_paint.c +++ b/src/openrct2/ride/track_paint.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../paint/supports.h" #include "../interface/viewport.h" diff --git a/src/openrct2/ride/vehicle.c b/src/openrct2/ride/vehicle.c index 41cc13061b..63261d081e 100644 --- a/src/openrct2/ride/vehicle.c +++ b/src/openrct2/ride/vehicle.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../audio/AudioMixer.h" -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../interface/viewport.h" diff --git a/src/openrct2/ride/water/river_rapids.c b/src/openrct2/ride/water/river_rapids.c index cd43bec882..61ec7d4bd3 100644 --- a/src/openrct2/ride/water/river_rapids.c +++ b/src/openrct2/ride/water/river_rapids.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../interface/viewport.h" #include "../../world/sprite.h" #include "../../paint/paint.h" diff --git a/src/openrct2/ride/water/splash_boats.c b/src/openrct2/ride/water/splash_boats.c index 06c4715c6a..06942a85c2 100644 --- a/src/openrct2/ride/water/splash_boats.c +++ b/src/openrct2/ride/water/splash_boats.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../../config.h" +#include "../../config/Config.h" #include "../../interface/viewport.h" #include "../../paint/paint.h" #include "../../paint/supports.h" diff --git a/src/openrct2/scenario/ScenarioRepository.cpp b/src/openrct2/scenario/ScenarioRepository.cpp index a060df524e..0b13a013ef 100644 --- a/src/openrct2/scenario/ScenarioRepository.cpp +++ b/src/openrct2/scenario/ScenarioRepository.cpp @@ -32,8 +32,9 @@ extern "C" { - #include "../config.h" + #include "../config/Config.h" #include "../localisation/localisation.h" + #include "../platform/platform.h" #include "../rct2.h" #include "scenario.h" } diff --git a/src/openrct2/scenario/scenario.c b/src/openrct2/scenario/scenario.c index b439ee333d..867b29db1b 100644 --- a/src/openrct2/scenario/scenario.c +++ b/src/openrct2/scenario/scenario.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../localisation/date.h" diff --git a/src/openrct2/scenario/scenario.h b/src/openrct2/scenario/scenario.h index f6959bda2f..3ca8a91945 100644 --- a/src/openrct2/scenario/scenario.h +++ b/src/openrct2/scenario/scenario.h @@ -21,7 +21,6 @@ #include "../management/finance.h" #include "../management/research.h" #include "../object.h" -#include "../platform/platform.h" #include "../rct12.h" #include "../rct2.h" #include "../rct2/addresses.h" @@ -382,7 +381,7 @@ extern rct_s6_info gS6Info; extern char gScenarioName[64]; extern char gScenarioDetails[256]; extern char gScenarioCompletedBy[32]; -extern char gScenarioSavePath[MAX_PATH]; +extern char gScenarioSavePath[260]; extern char gScenarioExpansionPacks[3256]; extern sint32 gFirstTimeSave; extern uint16 gSavedAge; diff --git a/src/openrct2/title/TitleScreen.cpp b/src/openrct2/title/TitleScreen.cpp index 9bda6890ea..24d02fdcbc 100644 --- a/src/openrct2/title/TitleScreen.cpp +++ b/src/openrct2/title/TitleScreen.cpp @@ -26,7 +26,7 @@ extern "C" { #include "../audio/audio.h" - #include "../config.h" + #include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/banner.c b/src/openrct2/windows/banner.c index ac1c58894b..fb3517368a 100644 --- a/src/openrct2/windows/banner.c +++ b/src/openrct2/windows/banner.c @@ -15,7 +15,7 @@ #pragma endregion #include "../game.h" -#include "../config.h" +#include "../config/Config.h" #include "../localisation/localisation.h" #include "../interface/viewport.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/cheats.c b/src/openrct2/windows/cheats.c index c28ea386e9..d6b166fbea 100644 --- a/src/openrct2/windows/cheats.c +++ b/src/openrct2/windows/cheats.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/custom_currency.c b/src/openrct2/windows/custom_currency.c index e5085076cf..f4d1b923f7 100644 --- a/src/openrct2/windows/custom_currency.c +++ b/src/openrct2/windows/custom_currency.c @@ -18,7 +18,7 @@ * 'Custom currency configuration' window definition and logic. */ -#include "../config.h" +#include "../config/Config.h" #include "../localisation/localisation.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/editor_bottom_toolbar.c b/src/openrct2/windows/editor_bottom_toolbar.c index 4cade3a608..d484d7b531 100644 --- a/src/openrct2/windows/editor_bottom_toolbar.c +++ b/src/openrct2/windows/editor_bottom_toolbar.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../editor.h" #include "../input.h" diff --git a/src/openrct2/windows/editor_object_selection.c b/src/openrct2/windows/editor_object_selection.c index 932fdd8dd1..8adbbb90fe 100644 --- a/src/openrct2/windows/editor_object_selection.c +++ b/src/openrct2/windows/editor_object_selection.c @@ -17,7 +17,7 @@ #pragma warning(disable : 4295) // 'identifier': array is too small to include a terminating null character #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../editor.h" #include "../interface/themes.h" diff --git a/src/openrct2/windows/error.c b/src/openrct2/windows/error.c index 85f03c308b..fe72033904 100644 --- a/src/openrct2/windows/error.c +++ b/src/openrct2/windows/error.c @@ -15,9 +15,10 @@ #pragma endregion #include "../audio/audio.h" -#include "../localisation/localisation.h" #include "../interface/widget.h" #include "../interface/window.h" +#include "../localisation/localisation.h" +#include "../platform/platform.h" #include "../rct2.h" #include "error.h" diff --git a/src/openrct2/windows/finances.c b/src/openrct2/windows/finances.c index 61a6a52419..10bb3d9430 100644 --- a/src/openrct2/windows/finances.c +++ b/src/openrct2/windows/finances.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/graph.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/game_bottom_toolbar.c b/src/openrct2/windows/game_bottom_toolbar.c index 9b2a1e6ae0..e91d8dff2b 100644 --- a/src/openrct2/windows/game_bottom_toolbar.c +++ b/src/openrct2/windows/game_bottom_toolbar.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../input.h" #include "../interface/themes.h" diff --git a/src/openrct2/windows/guest.c b/src/openrct2/windows/guest.c index 163350a2cc..40bce403d7 100644 --- a/src/openrct2/windows/guest.c +++ b/src/openrct2/windows/guest.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../input.h" #include "../management/marketing.h" diff --git a/src/openrct2/windows/guest_list.c b/src/openrct2/windows/guest_list.c index 5abe455c73..84ac5fa8a0 100644 --- a/src/openrct2/windows/guest_list.c +++ b/src/openrct2/windows/guest_list.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/themes.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/install_track.c b/src/openrct2/windows/install_track.c index 2cb179e3d7..ae8a3feee5 100644 --- a/src/openrct2/windows/install_track.c +++ b/src/openrct2/windows/install_track.c @@ -20,11 +20,12 @@ #include "../interface/widget.h" #include "../interface/window.h" #include "../localisation/localisation.h" +#include "../object/ObjectManager.h" +#include "../platform/platform.h" #include "../ride/ride.h" #include "../ride/track.h" #include "../ride/track_design.h" #include "../ride/TrackDesignRepository.h" -#include "../object/ObjectManager.h" #include "../sprites.h" #include "../util/util.h" #include "error.h" diff --git a/src/openrct2/windows/loadsave.c b/src/openrct2/windows/loadsave.c index ec4755079e..6dd59d621a 100644 --- a/src/openrct2/windows/loadsave.c +++ b/src/openrct2/windows/loadsave.c @@ -15,7 +15,7 @@ #pragma endregion #include -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../interface/themes.h" diff --git a/src/openrct2/windows/map_tooltip.c b/src/openrct2/windows/map_tooltip.c index 25c82a4c79..8b9c37ad78 100644 --- a/src/openrct2/windows/map_tooltip.c +++ b/src/openrct2/windows/map_tooltip.c @@ -14,10 +14,11 @@ *****************************************************************************/ #pragma endregion -#include "../localisation/localisation.h" #include "../input.h" #include "../interface/widget.h" #include "../interface/window.h" +#include "../localisation/localisation.h" +#include "../platform/platform.h" static rct_widget window_map_tooltip_widgets[] = { { WWT_IMGBTN, 0, 0, 199, 0, 29, 0xFFFFFFFF, STR_NONE }, diff --git a/src/openrct2/windows/multiplayer.c b/src/openrct2/windows/multiplayer.c index d351409c6e..514da162cc 100644 --- a/src/openrct2/windows/multiplayer.c +++ b/src/openrct2/windows/multiplayer.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/themes.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/new_campaign.c b/src/openrct2/windows/new_campaign.c index 247c6ccf00..204f3b6f7e 100644 --- a/src/openrct2/windows/new_campaign.c +++ b/src/openrct2/windows/new_campaign.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../localisation/localisation.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/new_ride.c b/src/openrct2/windows/new_ride.c index b6647735fb..796f965277 100644 --- a/src/openrct2/windows/new_ride.c +++ b/src/openrct2/windows/new_ride.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/news_options.c b/src/openrct2/windows/news_options.c index b81d0567fb..026eedef12 100644 --- a/src/openrct2/windows/news_options.c +++ b/src/openrct2/windows/news_options.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/widget.h" #include "../interface/window.h" #include "../localisation/localisation.h" @@ -33,23 +33,23 @@ typedef struct notification_def { } notification_def; static const notification_def NewsItemOptionDefinitions[] = { - { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_AWARD, offsetof(notification_configuration, park_award) }, - { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_MARKETING_CAMPAIGN_FINISHED, offsetof(notification_configuration, park_marketing_campaign_finished) }, - { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_WARNINGS, offsetof(notification_configuration, park_warnings) }, - { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_RATING_WARNINGS, offsetof(notification_configuration, park_rating_warnings) }, - { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_BROKEN_DOWN, offsetof(notification_configuration, ride_broken_down) }, - { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_CRASHED, offsetof(notification_configuration, ride_crashed) }, - { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_WARNINGS, offsetof(notification_configuration, ride_warnings) }, - { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_RESEARCHED, offsetof(notification_configuration, ride_researched) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_WARNINGS, offsetof(notification_configuration, guest_warnings) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LOST, offsetof(notification_configuration, guest_lost) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LEFT_PARK, offsetof(notification_configuration, guest_left_park) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_QUEUING_FOR_RIDE, offsetof(notification_configuration, guest_queuing_for_ride) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_ON_RIDE, offsetof(notification_configuration, guest_on_ride) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LEFT_RIDE, offsetof(notification_configuration, guest_left_ride) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_BOUGHT_ITEM, offsetof(notification_configuration, guest_bought_item) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_USED_FACILITY, offsetof(notification_configuration, guest_used_facility) }, - { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_DIED, offsetof(notification_configuration, guest_died) }, + { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_AWARD, offsetof(NotificationConfiguration, park_award) }, + { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_MARKETING_CAMPAIGN_FINISHED, offsetof(NotificationConfiguration, park_marketing_campaign_finished) }, + { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_WARNINGS, offsetof(NotificationConfiguration, park_warnings) }, + { NOTIFICATION_CATEGORY_PARK, STR_NOTIFICATION_PARK_RATING_WARNINGS, offsetof(NotificationConfiguration, park_rating_warnings) }, + { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_BROKEN_DOWN, offsetof(NotificationConfiguration, ride_broken_down) }, + { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_CRASHED, offsetof(NotificationConfiguration, ride_crashed) }, + { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_WARNINGS, offsetof(NotificationConfiguration, ride_warnings) }, + { NOTIFICATION_CATEGORY_RIDE, STR_NOTIFICATION_RIDE_RESEARCHED, offsetof(NotificationConfiguration, ride_researched) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_WARNINGS, offsetof(NotificationConfiguration, guest_warnings) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LOST, offsetof(NotificationConfiguration, guest_lost) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LEFT_PARK, offsetof(NotificationConfiguration, guest_left_park) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_QUEUING_FOR_RIDE, offsetof(NotificationConfiguration, guest_queuing_for_ride) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_ON_RIDE, offsetof(NotificationConfiguration, guest_on_ride) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_LEFT_RIDE, offsetof(NotificationConfiguration, guest_left_ride) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_BOUGHT_ITEM, offsetof(NotificationConfiguration, guest_bought_item) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_USED_FACILITY, offsetof(NotificationConfiguration, guest_used_facility) }, + { NOTIFICATION_CATEGORY_GUEST, STR_NOTIFICATION_GUEST_DIED, offsetof(NotificationConfiguration, guest_died) }, }; enum WINDOW_NEWS_WIDGET_IDX { diff --git a/src/openrct2/windows/options.c b/src/openrct2/windows/options.c index a4562c82d4..db33f67030 100644 --- a/src/openrct2/windows/options.c +++ b/src/openrct2/windows/options.c @@ -24,8 +24,9 @@ #include "../audio/audio.h" #include "../audio/AudioMixer.h" -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" +#include "../drawing/IDrawingEngine.h" #include "../interface/themes.h" #include "../interface/viewport.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/park.c b/src/openrct2/windows/park.c index 9184c614c8..b51a0f2b4f 100644 --- a/src/openrct2/windows/park.c +++ b/src/openrct2/windows/park.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../localisation/date.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/player.c b/src/openrct2/windows/player.c index 4fab90b0a4..e4a809cc49 100644 --- a/src/openrct2/windows/player.c +++ b/src/openrct2/windows/player.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../input.h" #include "../management/marketing.h" diff --git a/src/openrct2/windows/ride.c b/src/openrct2/windows/ride.c index ea7c25fe9a..e8176f75e0 100644 --- a/src/openrct2/windows/ride.c +++ b/src/openrct2/windows/ride.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../input.h" #include "../interface/themes.h" diff --git a/src/openrct2/windows/ride_construction.c b/src/openrct2/windows/ride_construction.c index 2f45222a2d..97ee941e07 100644 --- a/src/openrct2/windows/ride_construction.c +++ b/src/openrct2/windows/ride_construction.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/ride_list.c b/src/openrct2/windows/ride_list.c index 1cd866831e..7522a006b7 100644 --- a/src/openrct2/windows/ride_list.c +++ b/src/openrct2/windows/ride_list.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../ride/ride.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/save_prompt.c b/src/openrct2/windows/save_prompt.c index 14a82a3364..eacc28ae91 100644 --- a/src/openrct2/windows/save_prompt.c +++ b/src/openrct2/windows/save_prompt.c @@ -15,7 +15,7 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../localisation/localisation.h" #include "../interface/themes.h" diff --git a/src/openrct2/windows/server_list.c b/src/openrct2/windows/server_list.c index 63e505797b..729aabb888 100644 --- a/src/openrct2/windows/server_list.c +++ b/src/openrct2/windows/server_list.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/colour.h" #include "../interface/themes.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/server_start.c b/src/openrct2/windows/server_start.c index 5ccb8d112a..2667ccd5b1 100644 --- a/src/openrct2/windows/server_start.c +++ b/src/openrct2/windows/server_start.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/themes.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/shortcut_key_change.c b/src/openrct2/windows/shortcut_key_change.c index 90f0f753ab..5a9f60f654 100644 --- a/src/openrct2/windows/shortcut_key_change.c +++ b/src/openrct2/windows/shortcut_key_change.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/keyboard_shortcut.h" #include "../interface/themes.h" #include "../interface/window.h" diff --git a/src/openrct2/windows/shortcut_keys.c b/src/openrct2/windows/shortcut_keys.c index b361c557d7..29d39cc130 100644 --- a/src/openrct2/windows/shortcut_keys.c +++ b/src/openrct2/windows/shortcut_keys.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/window.h" #include "../interface/widget.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/sign.c b/src/openrct2/windows/sign.c index ca34ee7794..865e518f50 100644 --- a/src/openrct2/windows/sign.c +++ b/src/openrct2/windows/sign.c @@ -15,7 +15,7 @@ #pragma endregion #include "../game.h" -#include "../config.h" +#include "../config/Config.h" #include "../localisation/localisation.h" #include "../interface/viewport.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/staff.c b/src/openrct2/windows/staff.c index c9ba7217a0..0665f9ca17 100644 --- a/src/openrct2/windows/staff.c +++ b/src/openrct2/windows/staff.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/viewport.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/staff_list.c b/src/openrct2/windows/staff_list.c index 5f09ad4e97..496fe73a4b 100644 --- a/src/openrct2/windows/staff_list.c +++ b/src/openrct2/windows/staff_list.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/text_input.c b/src/openrct2/windows/text_input.c index c3da45c745..b748b6420c 100644 --- a/src/openrct2/windows/text_input.c +++ b/src/openrct2/windows/text_input.c @@ -21,7 +21,7 @@ * that is used for inputing new text for ride names and peep names. */ -#include "../config.h" +#include "../config/Config.h" #include "../platform/platform.h" #include "../interface/window.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/themes.c b/src/openrct2/windows/themes.c index b5c8db328b..85867e5ec6 100644 --- a/src/openrct2/windows/themes.c +++ b/src/openrct2/windows/themes.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../drawing/drawing.h" #include "../input.h" diff --git a/src/openrct2/windows/title_editor.c b/src/openrct2/windows/title_editor.c index 9dcb7eae06..706bbdd785 100644 --- a/src/openrct2/windows/title_editor.c +++ b/src/openrct2/windows/title_editor.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/title_exit.c b/src/openrct2/windows/title_exit.c index ac7823f0c5..f2d40c1346 100644 --- a/src/openrct2/windows/title_exit.c +++ b/src/openrct2/windows/title_exit.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../sprites.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/title_menu.c b/src/openrct2/windows/title_menu.c index cd82e98a43..c0126076dc 100644 --- a/src/openrct2/windows/title_menu.c +++ b/src/openrct2/windows/title_menu.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/title_options.c b/src/openrct2/windows/title_options.c index 3471b43c97..01a09fcf9c 100644 --- a/src/openrct2/windows/title_options.c +++ b/src/openrct2/windows/title_options.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../intro.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/title_scenarioselect.c b/src/openrct2/windows/title_scenarioselect.c index 38b9d018ab..2383048458 100644 --- a/src/openrct2/windows/title_scenarioselect.c +++ b/src/openrct2/windows/title_scenarioselect.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../audio/audio.h" #include "../localisation/date.h" #include "../localisation/localisation.h" diff --git a/src/openrct2/windows/top_toolbar.c b/src/openrct2/windows/top_toolbar.c index e5c9eaa87e..4608b1a769 100644 --- a/src/openrct2/windows/top_toolbar.c +++ b/src/openrct2/windows/top_toolbar.c @@ -16,7 +16,7 @@ #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../editor.h" #include "../game.h" #include "../input.h" diff --git a/src/openrct2/windows/track_list.c b/src/openrct2/windows/track_list.c index 122182ce26..7f86bcf992 100644 --- a/src/openrct2/windows/track_list.c +++ b/src/openrct2/windows/track_list.c @@ -15,7 +15,8 @@ #pragma endregion #include "../audio/audio.h" -#include "../config.h" +#include "../config/Config.h" +#include "../drawing/IDrawingEngine.h" #include "../editor.h" #include "../interface/themes.h" #include "../interface/widget.h" diff --git a/src/openrct2/windows/view_clipping.c b/src/openrct2/windows/view_clipping.c index 97607d4769..d2ca97cf91 100644 --- a/src/openrct2/windows/view_clipping.c +++ b/src/openrct2/windows/view_clipping.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include "../config.h" +#include "../config/Config.h" #include "../interface/themes.h" #include "../interface/widget.h" #include "../interface/window.h" diff --git a/src/openrct2/world/climate.c b/src/openrct2/world/climate.c index 2d4ab772cb..79c5ca8288 100644 --- a/src/openrct2/world/climate.c +++ b/src/openrct2/world/climate.c @@ -17,7 +17,7 @@ #include "../audio/audio.h" #include "../audio/AudioMixer.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../drawing/drawing.h" #include "../game.h" #include "../interface/window.h" diff --git a/src/openrct2/world/map.c b/src/openrct2/world/map.c index 24be817085..98e5d831f3 100644 --- a/src/openrct2/world/map.c +++ b/src/openrct2/world/map.c @@ -17,7 +17,7 @@ #include "../rct2/addresses.h" #include "../audio/audio.h" #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/Cursors.h" #include "../interface/window.h" diff --git a/src/openrct2/world/park.c b/src/openrct2/world/park.c index 5c5d0b5e1e..6101332ff7 100644 --- a/src/openrct2/world/park.c +++ b/src/openrct2/world/park.c @@ -15,7 +15,7 @@ #pragma endregion #include "../cheats.h" -#include "../config.h" +#include "../config/Config.h" #include "../game.h" #include "../interface/colour.h" #include "../interface/window.h" From 8d3bf515ed0c3ef8f62dc49315201f81cb624759 Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 19 Feb 2017 21:33:14 +0000 Subject: [PATCH 17/50] Fix trim function --- src/openrct2/core/String.cpp | 22 ++++++++++------------ 1 file changed, 10 insertions(+), 12 deletions(-) diff --git a/src/openrct2/core/String.cpp b/src/openrct2/core/String.cpp index bc8a0035a7..6921dc3eca 100644 --- a/src/openrct2/core/String.cpp +++ b/src/openrct2/core/String.cpp @@ -396,27 +396,21 @@ namespace String std::string Trim(const std::string &s) { - const utf8 * firstNonWhitespace = nullptr; - codepoint_t codepoint; const utf8 * ch = s.c_str(); const utf8 * nextCh; + const utf8 * firstNonWhitespace = nullptr; + const utf8 * lastNonWhitespace = nullptr; while ((codepoint = GetNextCodepoint(ch, &nextCh)) != '\0') { bool isWhiteSpace = codepoint <= WCHAR_MAX && iswspace((wchar_t)codepoint); - if (isWhiteSpace) - { - if (firstNonWhitespace != nullptr) - { - break; - } - } - else + if (!isWhiteSpace) { if (firstNonWhitespace == nullptr) { firstNonWhitespace = ch; } + lastNonWhitespace = ch; } ch = nextCh; } @@ -427,10 +421,14 @@ namespace String size_t newStringSize = ch - firstNonWhitespace; return std::string(firstNonWhitespace, newStringSize); } + else if (lastNonWhitespace != nullptr) + { + size_t newStringSize = lastNonWhitespace - s.c_str() + 1; + return std::string(s.c_str(), newStringSize); + } else { - size_t newStringSize = ch - s.c_str(); - return std::string(s.c_str(), newStringSize); + return std::string(); } } } From 87be032adc82d4a66cba7c096b5241c1ef2c7ecc Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 19 Feb 2017 21:37:06 +0000 Subject: [PATCH 18/50] Space out sections when writing config.ini --- src/openrct2/config/IniWriter.cpp | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp index bfee401403..04856ca677 100644 --- a/src/openrct2/config/IniWriter.cpp +++ b/src/openrct2/config/IniWriter.cpp @@ -22,7 +22,8 @@ class IniWriter final : public IIniWriter { private: - FileStream _fs; + FileStream _fs; + bool _firstSection = false; public: IniWriter(const std::string &path) @@ -32,6 +33,12 @@ public: void WriteSection(const std::string &name) override { + if (!_firstSection) + { + WriteLine(); + } + _firstSection = false; + WriteLine("[" + name + "]"); } @@ -78,10 +85,15 @@ private: WriteLine(name + " = " + value); } + void WriteLine() + { + _fs.Write(PLATFORM_NEWLINE, String::SizeOf(PLATFORM_NEWLINE)); + } + void WriteLine(const std::string &line) { _fs.Write(line.c_str(), line.size()); - _fs.Write(PLATFORM_NEWLINE, String::SizeOf(PLATFORM_NEWLINE)); + WriteLine(); } }; From a473740efd6f493ea7a8c09efbdf20ce6ac9ed3c Mon Sep 17 00:00:00 2001 From: Ted John Date: Sun, 19 Feb 2017 21:41:36 +0000 Subject: [PATCH 19/50] Fix build errors --- src/openrct2/config/IniWriter.cpp | 2 +- src/openrct2/network/network.cpp | 2 +- src/openrct2/platform/linux.c | 2 +- src/openrct2/platform/platform.h | 2 +- src/openrct2/platform/windows.c | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp index 04856ca677..57451e61a0 100644 --- a/src/openrct2/config/IniWriter.cpp +++ b/src/openrct2/config/IniWriter.cpp @@ -42,7 +42,7 @@ public: WriteLine("[" + name + "]"); } - void WriteBoolean(const std::string &name, bool value) + void WriteBoolean(const std::string &name, bool value) override { WriteProperty(name, value ? "true" : "false"); } diff --git a/src/openrct2/network/network.cpp b/src/openrct2/network/network.cpp index ce8ef1a5a9..260d3438e1 100644 --- a/src/openrct2/network/network.cpp +++ b/src/openrct2/network/network.cpp @@ -1628,7 +1628,7 @@ void Network::Server_Handle_AUTH(NetworkConnection& connection, NetworkPacket& p } } - if (gConfigNetwork.maxplayers <= player_list.size()) { + if ((size_t)gConfigNetwork.maxplayers <= player_list.size()) { connection.AuthStatus = NETWORK_AUTH_FULL; } else if (connection.AuthStatus == NETWORK_AUTH_VERIFIED) { diff --git a/src/openrct2/platform/linux.c b/src/openrct2/platform/linux.c index 252232f9a2..79bb4c1bb3 100644 --- a/src/openrct2/platform/linux.c +++ b/src/openrct2/platform/linux.c @@ -461,7 +461,7 @@ bool platform_open_common_file_dialog(utf8 *outFilename, file_dialog_desc *desc, return 1; } -utf8 *platform_open_directory_browser(utf8 *title) { +utf8 *platform_open_directory_browser(const utf8 *title) { size_t size; dialog_type dtype; sint32 exit_value; diff --git a/src/openrct2/platform/platform.h b/src/openrct2/platform/platform.h index 29a81740b7..df2181f2c5 100644 --- a/src/openrct2/platform/platform.h +++ b/src/openrct2/platform/platform.h @@ -195,7 +195,7 @@ void platform_get_user_directory(utf8 *outPath, const utf8 *subDirectory, size_t utf8* platform_get_username(); void platform_show_messagebox(const utf8 * message); bool platform_open_common_file_dialog(utf8 *outFilename, file_dialog_desc *desc, size_t outSize); -utf8 *platform_open_directory_browser(utf8 *title); +utf8 *platform_open_directory_browser(const utf8 *title); uint8 platform_get_locale_currency(); uint8 platform_get_currency_value(const char *currencyCode); uint16 platform_get_locale_language(); diff --git a/src/openrct2/platform/windows.c b/src/openrct2/platform/windows.c index 6af069d80f..fa568c323d 100644 --- a/src/openrct2/platform/windows.c +++ b/src/openrct2/platform/windows.c @@ -694,7 +694,7 @@ bool platform_open_common_file_dialog(utf8 *outFilename, file_dialog_desc *desc, return result; } -utf8 *platform_open_directory_browser(utf8 *title) +utf8 *platform_open_directory_browser(const utf8 *title) { BROWSEINFOW bi; wchar_t pszBuffer[MAX_PATH], wctitle[256]; From 80c4e4309dd5b51e96e0e18368ecb71dee8c331e Mon Sep 17 00:00:00 2001 From: Ted John Date: Mon, 20 Feb 2017 20:04:05 +0000 Subject: [PATCH 20/50] Remove duplicate entries and in wrong enum --- src/openrct2/config/Config.cpp | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 50d1e4917e..f7634fe0c7 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -50,9 +50,6 @@ namespace Config static auto Enum_Currency = ConfigEnum( { - ConfigEnumEntry("IMPERIAL", MEASUREMENT_FORMAT_IMPERIAL), - ConfigEnumEntry("METRIC", MEASUREMENT_FORMAT_METRIC), - ConfigEnumEntry("SI", MEASUREMENT_FORMAT_SI), ConfigEnumEntry("GBP", CURRENCY_POUNDS), ConfigEnumEntry("USD", CURRENCY_DOLLARS), ConfigEnumEntry("FRF", CURRENCY_FRANC), From 8ba5db069755c968a6cdc671742d190bc59a18b1 Mon Sep 17 00:00:00 2001 From: Ted John Date: Mon, 20 Feb 2017 20:05:59 +0000 Subject: [PATCH 21/50] Fix build for some configurations --- src/openrct2/drawing/lightfx.h | 1 + test/testpaint/compat.c | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/openrct2/drawing/lightfx.h b/src/openrct2/drawing/lightfx.h index d61b79a1d6..1d59bbfa12 100644 --- a/src/openrct2/drawing/lightfx.h +++ b/src/openrct2/drawing/lightfx.h @@ -19,6 +19,7 @@ #ifdef __ENABLE_LIGHTFX__ +#include #include "../common.h" #include "drawing.h" diff --git a/test/testpaint/compat.c b/test/testpaint/compat.c index 7b8a1a671e..f2bfd71e1e 100644 --- a/test/testpaint/compat.c +++ b/test/testpaint/compat.c @@ -14,7 +14,7 @@ *****************************************************************************/ #pragma endregion -#include +#include #include #include #include From 4f852d1ea5a9181efbf5041f2953459ae8a41d4d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Tue, 21 Feb 2017 07:29:06 +0100 Subject: [PATCH 22/50] Fix testpaint target for new config --- test/testpaint/compat.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/test/testpaint/compat.c b/test/testpaint/compat.c index f2bfd71e1e..9260c53e97 100644 --- a/test/testpaint/compat.c +++ b/test/testpaint/compat.c @@ -72,8 +72,7 @@ int object_entry_group_counts[] = { 1 // scenario text }; - -general_configuration gConfigGeneral; +GeneralConfiguration gConfigGeneral; uint16 gMapSelectFlags; uint16 gMapSelectType; rct_xy16 gMapSelectPositionA; From f4dfecf988c25c81c95f27564b08c40b09dce81f Mon Sep 17 00:00:00 2001 From: LRFLEW Date: Tue, 21 Feb 2017 01:51:05 -0600 Subject: [PATCH 23/50] Update Xcode Project --- OpenRCT2.xcodeproj/project.pbxproj | 38 +++++++++++++++++++++++++----- 1 file changed, 32 insertions(+), 6 deletions(-) diff --git a/OpenRCT2.xcodeproj/project.pbxproj b/OpenRCT2.xcodeproj/project.pbxproj index b7715d83b8..ddcb5ca522 100644 --- a/OpenRCT2.xcodeproj/project.pbxproj +++ b/OpenRCT2.xcodeproj/project.pbxproj @@ -244,6 +244,10 @@ D41B741D1C210A7A0080A7B9 /* libiconv.tbd in Frameworks */ = {isa = PBXBuildFile; fileRef = D41B741C1C210A7A0080A7B9 /* libiconv.tbd */; }; D41B74731C2125E50080A7B9 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = D41B74721C2125E50080A7B9 /* Assets.xcassets */; }; D429FF421E36ABCD009342A6 /* tile_inspector.c in Sources */ = {isa = PBXBuildFile; fileRef = D429FF401E36ABCD009342A6 /* tile_inspector.c */; }; + D42E337D1E5C27D600D630AF /* Config.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D42E33751E5C27D600D630AF /* Config.cpp */; }; + D42E337E1E5C27D600D630AF /* IniReader.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D42E33781E5C27D600D630AF /* IniReader.cpp */; }; + D42E337F1E5C27D600D630AF /* IniWriter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D42E337A1E5C27D600D630AF /* IniWriter.cpp */; }; + D42E33801E5C27D600D630AF /* KeyboardShortcuts.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D42E337C1E5C27D600D630AF /* KeyboardShortcuts.cpp */; }; D433A5001E4A861F00D9A6DF /* SawyerChunk.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D433A4FA1E4A861F00D9A6DF /* SawyerChunk.cpp */; }; D433A5011E4A861F00D9A6DF /* SawyerChunkReader.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D433A4FC1E4A861F00D9A6DF /* SawyerChunkReader.cpp */; }; D433A5021E4A861F00D9A6DF /* SawyerChunkWriter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D433A4FE1E4A861F00D9A6DF /* SawyerChunkWriter.cpp */; }; @@ -266,7 +270,6 @@ D44271FB1CC81B3200D84D28 /* ScreenshotCommands.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D44270DA1CC81B3200D84D28 /* ScreenshotCommands.cpp */; }; D44271FC1CC81B3200D84D28 /* SpriteCommands.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D44270DB1CC81B3200D84D28 /* SpriteCommands.cpp */; }; D44271FD1CC81B3200D84D28 /* cmdline_sprite.c in Sources */ = {isa = PBXBuildFile; fileRef = D44270DC1CC81B3200D84D28 /* cmdline_sprite.c */; }; - D44271FE1CC81B3200D84D28 /* config.c in Sources */ = {isa = PBXBuildFile; fileRef = D44270DE1CC81B3200D84D28 /* config.c */; }; D44271FF1CC81B3200D84D28 /* Console.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D44270E11CC81B3200D84D28 /* Console.cpp */; }; D44272001CC81B3200D84D28 /* Diagnostics.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D44270E31CC81B3200D84D28 /* Diagnostics.cpp */; }; D44272011CC81B3200D84D28 /* Guard.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D44270E71CC81B3200D84D28 /* Guard.cpp */; }; @@ -719,6 +722,14 @@ D429FF3F1E36ABB3009342A6 /* tile_inspector.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = tile_inspector.h; sourceTree = ""; }; D429FF401E36ABCD009342A6 /* tile_inspector.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = tile_inspector.c; sourceTree = ""; }; D429FF411E36ABCD009342A6 /* tile_inspector.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = tile_inspector.h; sourceTree = ""; }; + D42E33751E5C27D600D630AF /* Config.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Config.cpp; sourceTree = ""; }; + D42E33761E5C27D600D630AF /* Config.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Config.h; sourceTree = ""; }; + D42E33771E5C27D600D630AF /* ConfigEnum.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ConfigEnum.h; sourceTree = ""; }; + D42E33781E5C27D600D630AF /* IniReader.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = IniReader.cpp; sourceTree = ""; }; + D42E33791E5C27D600D630AF /* IniReader.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = IniReader.h; sourceTree = ""; }; + D42E337A1E5C27D600D630AF /* IniWriter.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = IniWriter.cpp; sourceTree = ""; }; + D42E337B1E5C27D600D630AF /* IniWriter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = IniWriter.h; sourceTree = ""; }; + D42E337C1E5C27D600D630AF /* KeyboardShortcuts.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = KeyboardShortcuts.cpp; sourceTree = ""; }; D433A4FA1E4A861F00D9A6DF /* SawyerChunk.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SawyerChunk.cpp; path = rct12/SawyerChunk.cpp; sourceTree = ""; }; D433A4FB1E4A861F00D9A6DF /* SawyerChunk.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = SawyerChunk.h; path = rct12/SawyerChunk.h; sourceTree = ""; }; D433A4FC1E4A861F00D9A6DF /* SawyerChunkReader.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SawyerChunkReader.cpp; path = rct12/SawyerChunkReader.cpp; sourceTree = ""; }; @@ -761,8 +772,6 @@ D44270DB1CC81B3200D84D28 /* SpriteCommands.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = SpriteCommands.cpp; sourceTree = ""; usesTabs = 0; }; D44270DC1CC81B3200D84D28 /* cmdline_sprite.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = cmdline_sprite.c; sourceTree = ""; }; D44270DD1CC81B3200D84D28 /* common.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = common.h; sourceTree = ""; }; - D44270DE1CC81B3200D84D28 /* config.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = config.c; sourceTree = ""; }; - D44270DF1CC81B3200D84D28 /* config.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = config.h; sourceTree = ""; }; D44270E11CC81B3200D84D28 /* Console.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Console.cpp; sourceTree = ""; usesTabs = 0; }; D44270E21CC81B3200D84D28 /* Console.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Console.hpp; sourceTree = ""; usesTabs = 0; }; D44270E31CC81B3200D84D28 /* Diagnostics.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Diagnostics.cpp; sourceTree = ""; usesTabs = 0; }; @@ -1536,6 +1545,7 @@ children = ( D44270CF1CC81B3200D84D28 /* audio */, D44270D61CC81B3200D84D28 /* cmdline */, + D42E33741E5C27D600D630AF /* config */, D44270E01CC81B3200D84D28 /* core */, D44271001CC81B3200D84D28 /* drawing */, D44271181CC81B3200D84D28 /* interface */, @@ -1559,8 +1569,6 @@ D44270D51CC81B3200D84D28 /* cheats.h */, D44270DC1CC81B3200D84D28 /* cmdline_sprite.c */, D44270DD1CC81B3200D84D28 /* common.h */, - D44270DE1CC81B3200D84D28 /* config.c */, - D44270DF1CC81B3200D84D28 /* config.h */, D44270FE1CC81B3200D84D28 /* diagnostic.c */, D44270FF1CC81B3200D84D28 /* diagnostic.h */, D442710E1CC81B3200D84D28 /* editor.c */, @@ -1607,6 +1615,21 @@ path = libxc; sourceTree = ""; }; + D42E33741E5C27D600D630AF /* config */ = { + isa = PBXGroup; + children = ( + D42E33751E5C27D600D630AF /* Config.cpp */, + D42E33761E5C27D600D630AF /* Config.h */, + D42E33771E5C27D600D630AF /* ConfigEnum.h */, + D42E33781E5C27D600D630AF /* IniReader.cpp */, + D42E33791E5C27D600D630AF /* IniReader.h */, + D42E337A1E5C27D600D630AF /* IniWriter.cpp */, + D42E337B1E5C27D600D630AF /* IniWriter.h */, + D42E337C1E5C27D600D630AF /* KeyboardShortcuts.cpp */, + ); + path = config; + sourceTree = ""; + }; D43407BF1D0E14BE00C2B3D4 /* opengl */ = { isa = PBXGroup; children = ( @@ -2723,6 +2746,7 @@ D44272001CC81B3200D84D28 /* Diagnostics.cpp in Sources */, D464FEF11D31A6AA00CBABAC /* SmallSceneryObject.cpp in Sources */, D44272471CC81B3200D84D28 /* ride_ratings.c in Sources */, + D42E337D1E5C27D600D630AF /* Config.cpp in Sources */, D44272721CC81B3200D84D28 /* new_campaign.c in Sources */, C686F93A1CDBC3B7009F9BFC /* spiral_slide.c in Sources */, C686F9421CDBC3B7009F9BFC /* magic_carpet.c in Sources */, @@ -2788,6 +2812,7 @@ D49766831D03B9FE002222CD /* SoftwareDrawingEngine.cpp in Sources */, C6E96E121E04067A0076A04F /* File.cpp in Sources */, D464FEF21D31A6AA00CBABAC /* StexObject.cpp in Sources */, + D42E33801E5C27D600D630AF /* KeyboardShortcuts.cpp in Sources */, C6E96E311E04072F0076A04F /* TitleSequenceManager.cpp in Sources */, C686F9331CDBC3B7009F9BFC /* maze.c in Sources */, C686F9241CDBC3B7009F9BFC /* suspended_swinging_coaster.c in Sources */, @@ -2806,12 +2831,14 @@ D44272571CC81B3200D84D28 /* clear_scenery.c in Sources */, D442727D1CC81B3200D84D28 /* ride_list.c in Sources */, C686F94E1CDBC3B7009F9BFC /* boat_ride.c in Sources */, + D42E337F1E5C27D600D630AF /* IniWriter.cpp in Sources */, D44272891CC81B3200D84D28 /* themes.c in Sources */, C686F9531CDBC3B7009F9BFC /* splash_boats.c in Sources */, C686F9441CDBC3B7009F9BFC /* pirate_ship.c in Sources */, 652747EC1E41CE1B000F36FD /* SawyerEncoding.cpp in Sources */, D44272791CC81B3200D84D28 /* publisher_credits.c in Sources */, C686F91E1CDBC3B7009F9BFC /* reverse_freefall_coaster.c in Sources */, + D42E337E1E5C27D600D630AF /* IniReader.cpp in Sources */, D442723B1CC81B3200D84D28 /* crash.cpp in Sources */, C650B21A1CCABBDD00B4D91C /* tables.cpp in Sources */, D44272291CC81B3200D84D28 /* LanguagePack.cpp in Sources */, @@ -3008,7 +3035,6 @@ C686F9111CDBC3B7009F9BFC /* heartline_twister_coaster.c in Sources */, C6834A111DFDE8E300CE933A /* interop.c in Sources */, C686F9231CDBC3B7009F9BFC /* steeplechase.c in Sources */, - D44271FE1CC81B3200D84D28 /* config.c in Sources */, D44272871CC81B3200D84D28 /* staff_list.c in Sources */, ); runOnlyForDeploymentPostprocessing = 0; From f9c2d83393f44aef68167962467550b6afbd7bef Mon Sep 17 00:00:00 2001 From: LRFLEW Date: Tue, 21 Feb 2017 01:51:35 -0600 Subject: [PATCH 24/50] Include new config header in macos.m --- src/openrct2/platform/macos.m | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/openrct2/platform/macos.m b/src/openrct2/platform/macos.m index 77b67b8808..87116b6e70 100644 --- a/src/openrct2/platform/macos.m +++ b/src/openrct2/platform/macos.m @@ -22,7 +22,7 @@ #include "platform.h" #include "../util/util.h" #include "../localisation/language.h" -#include "../config.h" +#include "../config/Config.h" bool platform_check_steam_overlay_attached() { STUB(); @@ -105,7 +105,7 @@ void platform_show_messagebox(const char * message) } } -utf8 *platform_open_directory_browser(utf8 *title) +utf8 *platform_open_directory_browser(const utf8 *title) { @autoreleasepool { From a9ffe5bf6d0d12b14da967da52c6ddbb985af1b6 Mon Sep 17 00:00:00 2001 From: Ted John Date: Tue, 21 Feb 2017 12:11:19 +0000 Subject: [PATCH 25/50] Convert tabs to spaces in KeyboardShortcuts.cpp --- src/openrct2/config/KeyboardShortcuts.cpp | 103 +++++++++++----------- 1 file changed, 50 insertions(+), 53 deletions(-) diff --git a/src/openrct2/config/KeyboardShortcuts.cpp b/src/openrct2/config/KeyboardShortcuts.cpp index e2b9272188..765f46b337 100644 --- a/src/openrct2/config/KeyboardShortcuts.cpp +++ b/src/openrct2/config/KeyboardShortcuts.cpp @@ -35,59 +35,56 @@ namespace KeyboardShortcuts // Default keyboard shortcuts static const uint16 _defaultShortcutKeys[SHORTCUT_COUNT] = { - SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_TOP_MOST_WINDOW - SHIFT | SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS - SDL_SCANCODE_ESCAPE, // SHORTCUT_CANCEL_CONSTRUCTION_MODE - SDL_SCANCODE_PAUSE, // SHORTCUT_PAUSE_GAME - SDL_SCANCODE_PAGEUP, // SHORTCUT_ZOOM_VIEW_OUT - SDL_SCANCODE_PAGEDOWN, // SHORTCUT_ZOOM_VIEW_IN - SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_CLOCKWISE - SHIFT | SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE - SDL_SCANCODE_Z, // SHORTCUT_ROTATE_CONSTRUCTION_OBJECT - SDL_SCANCODE_1, // SHORTCUT_UNDERGROUND_VIEW_TOGGLE - SDL_SCANCODE_H, // SHORTCUT_REMOVE_BASE_LAND_TOGGLE - SDL_SCANCODE_V, // SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE - SDL_SCANCODE_3, // SHORTCUT_SEE_THROUGH_RIDES_TOGGLE - SDL_SCANCODE_4, // SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE - SDL_SCANCODE_5, // SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE - SDL_SCANCODE_6, // SHORTCUT_INVISIBLE_PEOPLE_TOGGLE - SDL_SCANCODE_8, // SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE - SDL_SCANCODE_9, // SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE - SDL_SCANCODE_0, // SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE - SDL_SCANCODE_F1, // SHORTCUT_ADJUST_LAND - SDL_SCANCODE_F2, // SHORTCUT_ADJUST_WATER - SDL_SCANCODE_F3, // SHORTCUT_BUILD_SCENERY - SDL_SCANCODE_F4, // SHORTCUT_BUILD_PATHS - SDL_SCANCODE_F5, // SHORTCUT_BUILD_NEW_RIDE - SDL_SCANCODE_F, // SHORTCUT_SHOW_FINANCIAL_INFORMATION - SDL_SCANCODE_D, // SHORTCUT_SHOW_RESEARCH_INFORMATION - SDL_SCANCODE_R, // SHORTCUT_SHOW_RIDES_LIST - SDL_SCANCODE_P, // SHORTCUT_SHOW_PARK_INFORMATION - SDL_SCANCODE_G, // SHORTCUT_SHOW_GUEST_LIST - SDL_SCANCODE_S, // SHORTCUT_SHOW_STAFF_LIST - SDL_SCANCODE_M, // SHORTCUT_SHOW_RECENT_MESSAGES - SDL_SCANCODE_TAB, // SHORTCUT_SHOW_MAP - PLATFORM_MODIFIER | SDL_SCANCODE_S, // SHORTCUT_SCREENSHOT - - // New - SDL_SCANCODE_MINUS, // SHORTCUT_REDUCE_GAME_SPEED, - SDL_SCANCODE_EQUALS, // SHORTCUT_INCREASE_GAME_SPEED, - PLATFORM_MODIFIER | ALT | SDL_SCANCODE_C, // SHORTCUT_OPEN_CHEAT_WINDOW, - SDL_SCANCODE_T, // SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, - SDL_SCANCODE_UP, // SHORTCUT_SCROLL_MAP_UP - SDL_SCANCODE_LEFT, // SHORTCUT_SCROLL_MAP_LEFT - SDL_SCANCODE_DOWN, // SHORTCUT_SCROLL_MAP_DOWN - SDL_SCANCODE_RIGHT, // SHORTCUT_SCROLL_MAP_RIGHT - SDL_SCANCODE_C, // SHORTCUT_OPEN_CHAT_WINDOW - PLATFORM_MODIFIER | SDL_SCANCODE_F10, // SHORTCUT_QUICK_SAVE_GAME - - SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_OPTIONS - SHORTCUT_UNDEFINED, // SHORTCUT_MUTE_SOUND - ALT | SDL_SCANCODE_RETURN, // SHORTCUT_WINDOWED_MODE_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_MULTIPLAYER - SHORTCUT_UNDEFINED, // SHORTCUT_PAINT_ORIGINAL_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_DEBUG_PAINT_TOGGLE - SHORTCUT_UNDEFINED, // SHORTCUT_SEE_THROUGH_PATHS_TOGGLE + SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_TOP_MOST_WINDOW + SHIFT | SDL_SCANCODE_BACKSPACE, // SHORTCUT_CLOSE_ALL_FLOATING_WINDOWS + SDL_SCANCODE_ESCAPE, // SHORTCUT_CANCEL_CONSTRUCTION_MODE + SDL_SCANCODE_PAUSE, // SHORTCUT_PAUSE_GAME + SDL_SCANCODE_PAGEUP, // SHORTCUT_ZOOM_VIEW_OUT + SDL_SCANCODE_PAGEDOWN, // SHORTCUT_ZOOM_VIEW_IN + SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_CLOCKWISE + SHIFT | SDL_SCANCODE_RETURN, // SHORTCUT_ROTATE_VIEW_ANTICLOCKWISE + SDL_SCANCODE_Z, // SHORTCUT_ROTATE_CONSTRUCTION_OBJECT + SDL_SCANCODE_1, // SHORTCUT_UNDERGROUND_VIEW_TOGGLE + SDL_SCANCODE_H, // SHORTCUT_REMOVE_BASE_LAND_TOGGLE + SDL_SCANCODE_V, // SHORTCUT_REMOVE_VERTICAL_LAND_TOGGLE + SDL_SCANCODE_3, // SHORTCUT_SEE_THROUGH_RIDES_TOGGLE + SDL_SCANCODE_4, // SHORTCUT_SEE_THROUGH_SCENERY_TOGGLE + SDL_SCANCODE_5, // SHORTCUT_INVISIBLE_SUPPORTS_TOGGLE + SDL_SCANCODE_6, // SHORTCUT_INVISIBLE_PEOPLE_TOGGLE + SDL_SCANCODE_8, // SHORTCUT_HEIGHT_MARKS_ON_LAND_TOGGLE + SDL_SCANCODE_9, // SHORTCUT_HEIGHT_MARKS_ON_RIDE_TRACKS_TOGGLE + SDL_SCANCODE_0, // SHORTCUT_HEIGHT_MARKS_ON_PATHS_TOGGLE + SDL_SCANCODE_F1, // SHORTCUT_ADJUST_LAND + SDL_SCANCODE_F2, // SHORTCUT_ADJUST_WATER + SDL_SCANCODE_F3, // SHORTCUT_BUILD_SCENERY + SDL_SCANCODE_F4, // SHORTCUT_BUILD_PATHS + SDL_SCANCODE_F5, // SHORTCUT_BUILD_NEW_RIDE + SDL_SCANCODE_F, // SHORTCUT_SHOW_FINANCIAL_INFORMATION + SDL_SCANCODE_D, // SHORTCUT_SHOW_RESEARCH_INFORMATION + SDL_SCANCODE_R, // SHORTCUT_SHOW_RIDES_LIST + SDL_SCANCODE_P, // SHORTCUT_SHOW_PARK_INFORMATION + SDL_SCANCODE_G, // SHORTCUT_SHOW_GUEST_LIST + SDL_SCANCODE_S, // SHORTCUT_SHOW_STAFF_LIST + SDL_SCANCODE_M, // SHORTCUT_SHOW_RECENT_MESSAGES + SDL_SCANCODE_TAB, // SHORTCUT_SHOW_MAP + PLATFORM_MODIFIER | SDL_SCANCODE_S, // SHORTCUT_SCREENSHOT + SDL_SCANCODE_MINUS, // SHORTCUT_REDUCE_GAME_SPEED, + SDL_SCANCODE_EQUALS, // SHORTCUT_INCREASE_GAME_SPEED, + PLATFORM_MODIFIER | ALT | SDL_SCANCODE_C, // SHORTCUT_OPEN_CHEAT_WINDOW, + SDL_SCANCODE_T, // SHORTCUT_REMOVE_TOP_BOTTOM_TOOLBAR_TOGGLE, + SDL_SCANCODE_UP, // SHORTCUT_SCROLL_MAP_UP + SDL_SCANCODE_LEFT, // SHORTCUT_SCROLL_MAP_LEFT + SDL_SCANCODE_DOWN, // SHORTCUT_SCROLL_MAP_DOWN + SDL_SCANCODE_RIGHT, // SHORTCUT_SCROLL_MAP_RIGHT + SDL_SCANCODE_C, // SHORTCUT_OPEN_CHAT_WINDOW + PLATFORM_MODIFIER | SDL_SCANCODE_F10, // SHORTCUT_QUICK_SAVE_GAME + SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_OPTIONS + SHORTCUT_UNDEFINED, // SHORTCUT_MUTE_SOUND + ALT | SDL_SCANCODE_RETURN, // SHORTCUT_WINDOWED_MODE_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_SHOW_MULTIPLAYER + SHORTCUT_UNDEFINED, // SHORTCUT_PAINT_ORIGINAL_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_DEBUG_PAINT_TOGGLE + SHORTCUT_UNDEFINED, // SHORTCUT_SEE_THROUGH_PATHS_TOGGLE }; constexpr sint32 CURRENT_FILE_VERSION = 1; From 6e9d22e99d67909e06779e5e67ca3fa6a385137a Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 22 Feb 2017 17:46:10 +0000 Subject: [PATCH 26/50] Use hpp for header files ...as they contain C++ implementation code. --- src/openrct2/config/Config.cpp | 4 ++-- src/openrct2/config/{ConfigEnum.h => ConfigEnum.hpp} | 0 src/openrct2/config/IniReader.cpp | 2 +- src/openrct2/config/{IniReader.h => IniReader.hpp} | 2 +- src/openrct2/config/IniWriter.cpp | 2 +- src/openrct2/config/{IniWriter.h => IniWriter.hpp} | 2 +- src/openrct2/libopenrct2.vcxproj | 6 +++--- 7 files changed, 9 insertions(+), 9 deletions(-) rename src/openrct2/config/{ConfigEnum.h => ConfigEnum.hpp} (100%) rename src/openrct2/config/{IniReader.h => IniReader.hpp} (98%) rename src/openrct2/config/{IniWriter.h => IniWriter.hpp} (98%) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index f7634fe0c7..89b11af5fd 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -25,8 +25,8 @@ #include "../network/network.h" #include "../OpenRCT2.h" #include "Config.h" -#include "IniReader.h" -#include "IniWriter.h" +#include "IniReader.hpp" +#include "IniWriter.hpp" extern "C" { diff --git a/src/openrct2/config/ConfigEnum.h b/src/openrct2/config/ConfigEnum.hpp similarity index 100% rename from src/openrct2/config/ConfigEnum.h rename to src/openrct2/config/ConfigEnum.hpp diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index d203650f01..d732d25c47 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -23,7 +23,7 @@ #include "../core/FileStream.hpp" #include "../core/String.hpp" #include "../core/StringBuilder.hpp" -#include "IniReader.h" +#include "IniReader.hpp" struct Span { diff --git a/src/openrct2/config/IniReader.h b/src/openrct2/config/IniReader.hpp similarity index 98% rename from src/openrct2/config/IniReader.h rename to src/openrct2/config/IniReader.hpp index 9a2cf66d06..3b8df92550 100644 --- a/src/openrct2/config/IniReader.h +++ b/src/openrct2/config/IniReader.hpp @@ -16,7 +16,7 @@ #include #include "../common.h" -#include "ConfigEnum.h" +#include "ConfigEnum.hpp" interface IIniReader { diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp index 57451e61a0..bad2ca1a88 100644 --- a/src/openrct2/config/IniWriter.cpp +++ b/src/openrct2/config/IniWriter.cpp @@ -17,7 +17,7 @@ #include #include "../core/FileStream.hpp" #include "../platform/platform.h" -#include "IniWriter.h" +#include "IniWriter.hpp" class IniWriter final : public IIniWriter { diff --git a/src/openrct2/config/IniWriter.h b/src/openrct2/config/IniWriter.hpp similarity index 98% rename from src/openrct2/config/IniWriter.h rename to src/openrct2/config/IniWriter.hpp index be409f32ed..a323a91360 100644 --- a/src/openrct2/config/IniWriter.h +++ b/src/openrct2/config/IniWriter.hpp @@ -16,7 +16,7 @@ #include #include "../common.h" -#include "ConfigEnum.h" +#include "ConfigEnum.hpp" interface IIniWriter { diff --git a/src/openrct2/libopenrct2.vcxproj b/src/openrct2/libopenrct2.vcxproj index e16cd20dc9..1ae212c74d 100644 --- a/src/openrct2/libopenrct2.vcxproj +++ b/src/openrct2/libopenrct2.vcxproj @@ -423,9 +423,9 @@ - - - + + + From 4dc792bc1deaf2c2410de44d78581b100f302b86 Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 22 Feb 2017 17:52:33 +0000 Subject: [PATCH 27/50] Use IStream for IniReader and IniWriter --- src/openrct2/config/Config.cpp | 7 +++++-- src/openrct2/config/IniReader.cpp | 11 +++++------ src/openrct2/config/IniReader.hpp | 4 +++- src/openrct2/config/IniWriter.cpp | 14 +++++++------- src/openrct2/config/IniWriter.hpp | 4 +++- 5 files changed, 23 insertions(+), 17 deletions(-) diff --git a/src/openrct2/config/Config.cpp b/src/openrct2/config/Config.cpp index 89b11af5fd..753302ad97 100644 --- a/src/openrct2/config/Config.cpp +++ b/src/openrct2/config/Config.cpp @@ -17,6 +17,7 @@ #include #include "../core/Console.hpp" #include "../core/Exception.hpp" +#include "../core/FileStream.hpp" #include "../core/Memory.hpp" #include "../core/Path.hpp" #include "../core/String.hpp" @@ -505,7 +506,8 @@ namespace Config { try { - auto reader = std::unique_ptr(CreateIniReader(path)); + auto fs = FileStream(path, FILE_MODE_OPEN); + auto reader = std::unique_ptr(CreateIniReader(&fs)); ReadGeneral(reader.get()); ReadInterface(reader.get()); ReadSound(reader.get()); @@ -525,7 +527,8 @@ namespace Config { try { - auto writer = std::unique_ptr(CreateIniWriter(path)); + auto fs = FileStream(path, FILE_MODE_WRITE); + auto writer = std::unique_ptr(CreateIniWriter(&fs)); WriteGeneral(writer.get()); WriteInterface(writer.get()); WriteSound(writer.get()); diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index d732d25c47..4577deda72 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -60,12 +60,11 @@ private: std::unordered_map _values; public: - IniReader(const std::string &path) + IniReader(IStream * stream) { - auto fs = FileStream(path, FILE_MODE_OPEN); - uint64 length = fs.GetLength(); + uint64 length = stream->GetLength() - stream->GetPosition(); _buffer.resize(length); - fs.Read(_buffer.data(), length); + stream->Read(_buffer.data(), length); RemoveBOM(); @@ -368,9 +367,9 @@ utf8 * IIniReader::GetCString(const std::string &name, const utf8 * defaultValue return String::Duplicate(szValue.c_str()); } -IIniReader * CreateIniReader(const std::string &path) +IIniReader * CreateIniReader(IStream * stream) { - return new IniReader(path); + return new IniReader(stream); } IIniReader * CreateDefaultIniReader() diff --git a/src/openrct2/config/IniReader.hpp b/src/openrct2/config/IniReader.hpp index 3b8df92550..e5fee1c671 100644 --- a/src/openrct2/config/IniReader.hpp +++ b/src/openrct2/config/IniReader.hpp @@ -18,6 +18,8 @@ #include "../common.h" #include "ConfigEnum.hpp" +interface IStream; + interface IIniReader { virtual ~IIniReader() = default; @@ -45,5 +47,5 @@ interface IIniReader utf8 * GetCString(const std::string &name, const utf8 * defaultValue) const; }; -IIniReader * CreateIniReader(const std::string &path); +IIniReader * CreateIniReader(IStream * stream); IIniReader * CreateDefaultIniReader(); diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp index bad2ca1a88..c09e23a262 100644 --- a/src/openrct2/config/IniWriter.cpp +++ b/src/openrct2/config/IniWriter.cpp @@ -22,12 +22,12 @@ class IniWriter final : public IIniWriter { private: - FileStream _fs; + IStream * _stream; bool _firstSection = false; public: - IniWriter(const std::string &path) - : _fs(path, FILE_MODE_WRITE) + IniWriter(IStream * stream) + : _stream(stream) { } @@ -87,12 +87,12 @@ private: void WriteLine() { - _fs.Write(PLATFORM_NEWLINE, String::SizeOf(PLATFORM_NEWLINE)); + _stream->Write(PLATFORM_NEWLINE, String::SizeOf(PLATFORM_NEWLINE)); } void WriteLine(const std::string &line) { - _fs.Write(line.c_str(), line.size()); + _stream->Write(line.c_str(), line.size()); WriteLine(); } }; @@ -102,7 +102,7 @@ void IIniWriter::WriteString(const std::string &name, const utf8 * value) WriteString(name, String::ToStd(value)); } -IIniWriter * CreateIniWriter(const std::string &path) +IIniWriter * CreateIniWriter(IStream * stream) { - return new IniWriter(path); + return new IniWriter(stream); } diff --git a/src/openrct2/config/IniWriter.hpp b/src/openrct2/config/IniWriter.hpp index a323a91360..434d710116 100644 --- a/src/openrct2/config/IniWriter.hpp +++ b/src/openrct2/config/IniWriter.hpp @@ -18,6 +18,8 @@ #include "../common.h" #include "ConfigEnum.hpp" +interface IStream; + interface IIniWriter { virtual ~IIniWriter() = default; @@ -47,4 +49,4 @@ interface IIniWriter void WriteString(const std::string &name, const utf8 * value); }; -IIniWriter * CreateIniWriter(const std::string &path); +IIniWriter * CreateIniWriter(IStream * stream); From d72ced4ea9ea029e993b1f255d1a014ae8b88f98 Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 22 Feb 2017 17:54:37 +0000 Subject: [PATCH 28/50] Remove final from struct --- src/openrct2/config/ConfigEnum.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/openrct2/config/ConfigEnum.hpp b/src/openrct2/config/ConfigEnum.hpp index 5cd0c231e0..b29769f785 100644 --- a/src/openrct2/config/ConfigEnum.hpp +++ b/src/openrct2/config/ConfigEnum.hpp @@ -21,7 +21,7 @@ #include "../core/String.hpp" template -struct ConfigEnumEntry final +struct ConfigEnumEntry { std::string Key; T Value; From 40eb2c55fdc74232a700e76399feb3e8d5d69158 Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 22 Feb 2017 17:58:50 +0000 Subject: [PATCH 29/50] Reduce duplicated code in IniReader --- src/openrct2/config/IniReader.cpp | 42 ++++++++++++++----------------- 1 file changed, 19 insertions(+), 23 deletions(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 4577deda72..4df1ee9e4d 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -93,49 +93,45 @@ public: bool GetBoolean(const std::string &name, bool defaultValue) const override { - auto it = _values.find(name); - if (it == _values.end()) + bool result = defaultValue; + std::string value; + if (TryGetString(name, &value)) { - return defaultValue; + result = String::Equals(value, "true", true); } - - std::string value = it->second; - return String::Equals(value, "true", true); + return result; } sint32 GetSint32(const std::string &name, sint32 defaultValue) const override { - auto it = _values.find(name); - if (it == _values.end()) + sint32 result = defaultValue; + std::string value; + if (TryGetString(name, &value)) { - return defaultValue; + result = std::stoi(value); } - - std::string value = it->second; - return std::stoi(value); + return result; } float GetFloat(const std::string &name, float defaultValue) const override { - auto it = _values.find(name); - if (it == _values.end()) + float result = defaultValue; + std::string value; + if (TryGetString(name, &value)) { - return defaultValue; + result = std::stof(value); } - - std::string value = it->second; - return std::stof(value); + return result; } std::string GetString(const std::string &name, const std::string &defaultValue) const override { - auto it = _values.find(name); - if (it == _values.end()) + std::string result; + if (TryGetString(name, &result)) { - return defaultValue; + result = defaultValue; } - - return it->second; + return result; } bool TryGetString(const std::string &name, std::string * outValue) const override From 9ba51f221b011a7d0a863e8873e3eb1641b13d95 Mon Sep 17 00:00:00 2001 From: Ted John Date: Wed, 22 Feb 2017 18:00:19 +0000 Subject: [PATCH 30/50] Add summary comments --- src/openrct2/config/IniReader.cpp | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 4df1ee9e4d..1ba131e70d 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -25,6 +25,9 @@ #include "../core/StringBuilder.hpp" #include "IniReader.hpp" +/** + * Simple tuple (start, length) representing a text span in a buffer. + */ struct Span { size_t Start = 0; @@ -38,6 +41,9 @@ struct Span } }; +/** + * Simple tuple (start, end) inclusive representing a range of lines. + */ struct LineRange { size_t Start = 0; From 9c32cb3a6271c0c06e9a5462a7cb31bb982f5643 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Thu, 23 Feb 2017 23:24:26 +0100 Subject: [PATCH 31/50] Don't break on too short INI streams --- src/openrct2/config/IniReader.cpp | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 1ba131e70d..5a6398f9ac 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -76,7 +76,7 @@ public: // Ensure there is a null terminator on the end, this is // mainly for ParseLines's sake - if (_buffer[length - 1] != 0) + if (_buffer.empty() || _buffer[length - 1] != 0) { _buffer.push_back(0); } @@ -155,6 +155,10 @@ public: private: void RemoveBOM() { + if (_buffer.size() < 3) + { + return; + } utf8 * file = (utf8 *)_buffer.data(); utf8 * content = String::SkipBOM(file); if (file != content) From 1784543e14aa9aae8eef6252f7b40e599d949f57 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Thu, 23 Feb 2017 23:25:10 +0100 Subject: [PATCH 32/50] Set default first section to true --- src/openrct2/config/IniWriter.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/openrct2/config/IniWriter.cpp b/src/openrct2/config/IniWriter.cpp index c09e23a262..e846018ed3 100644 --- a/src/openrct2/config/IniWriter.cpp +++ b/src/openrct2/config/IniWriter.cpp @@ -23,7 +23,7 @@ class IniWriter final : public IIniWriter { private: IStream * _stream; - bool _firstSection = false; + bool _firstSection = true; public: IniWriter(IStream * stream) From 8143be0707b9252652dc9a99a28c1927054a856b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Thu, 23 Feb 2017 23:26:11 +0100 Subject: [PATCH 33/50] Add IniReader, IniWriter tests --- test/tests/CMakeLists.txt | 23 +++++ test/tests/IniReaderTest.cpp | 66 ++++++++++++ test/tests/IniWriterTest.cpp | 193 +++++++++++++++++++++++++++++++++++ 3 files changed, 282 insertions(+) create mode 100644 test/tests/IniReaderTest.cpp create mode 100644 test/tests/IniWriterTest.cpp diff --git a/test/tests/CMakeLists.txt b/test/tests/CMakeLists.txt index f92f61bae8..6dcf7cb79a 100644 --- a/test/tests/CMakeLists.txt +++ b/test/tests/CMakeLists.txt @@ -86,3 +86,26 @@ set(LANGUAGEPACK_TEST_SOURCES add_executable(test_languagepack ${LANGUAGEPACK_TEST_SOURCES}) target_link_libraries(test_languagepack ${GTEST_LIBRARIES} dl z SDL2 SDL2_ttf ssl crypto) add_test(NAME languagepack COMMAND test_languagepack) + + +# LanguagePack test +set(INI_TEST_SOURCES + "IniWriterTest.cpp" + "IniReaderTest.cpp" + "../../src/openrct2/config/IniReader.cpp" + "../../src/openrct2/config/IniWriter.cpp" + "../../src/openrct2/core/Console.cpp" + "../../src/openrct2/core/Diagnostics.cpp" + "../../src/openrct2/core/Guard.cpp" + "../../src/openrct2/core/IStream.cpp" + "../../src/openrct2/core/MemoryStream.cpp" + "../../src/openrct2/core/String.cpp" + "../../src/openrct2/diagnostic.c" + "../../src/openrct2/localisation/format_codes.c" + "../../src/openrct2/localisation/utf8.c" + "../../src/openrct2/util/util.c" + "../../src/openrct2/Version.cpp" + ) +add_executable(test_ini ${INI_TEST_SOURCES}) +target_link_libraries(test_ini ${GTEST_LIBRARIES} dl z) +add_test(NAME ini COMMAND test_ini) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp new file mode 100644 index 0000000000..9a8d0740ca --- /dev/null +++ b/test/tests/IniReaderTest.cpp @@ -0,0 +1,66 @@ +#include +#include +#include "openrct2/config/ConfigEnum.hpp" +#include "openrct2/config/IniReader.hpp" +#include "openrct2/core/MemoryStream.h" +#include "openrct2/core/Util.hpp" + +class IniReaderTest : public testing::Test +{ +protected: + static const utf8 predefined[]; +}; + +static auto Enum_Currency = ConfigEnum({}); + +TEST_F(IniReaderTest, create_empty) +{ + MemoryStream * ms = new MemoryStream(0); + ASSERT_NE(ms, nullptr); + ASSERT_EQ(ms->CanRead(), true); + ASSERT_EQ(ms->CanWrite(), true); + IIniReader * ir = CreateIniReader(ms); + ASSERT_NE(ir, nullptr); + ASSERT_EQ(ir->GetBoolean("nobody", true), true); + ASSERT_EQ(ir->GetCString("expects", nullptr), nullptr); + ASSERT_EQ(ir->GetEnum("spanish", 12345, Enum_Currency), 12345); + ASSERT_EQ(ir->GetFloat("inquisition", 1.234f), 1.234f); + ASSERT_EQ(ir->GetSint32("universal_answer", 42), 42); + delete ir; + delete ms; +} + +TEST_F(IniReaderTest, read_prepared) +{ + MemoryStream * ms = new MemoryStream(predefined, 99); + ASSERT_NE(ms, nullptr); + ASSERT_EQ(ms->CanRead(), true); + ASSERT_EQ(ms->CanWrite(), false); + IIniReader * ir = CreateIniReader(ms); + ASSERT_NE(ir, nullptr); + ASSERT_EQ(ir->ReadSection("doesnt_exist"), false); + ASSERT_EQ(ir->ReadSection("bool"), true); + // name of section + ASSERT_EQ(ir->GetSint32("bool", 42), 42); + // value from different section + ASSERT_EQ(ir->GetSint32("one", 42), 42); + // existing value as different type + EXPECT_THROW(ir->GetSint32("boolval", 42), std::invalid_argument); + ASSERT_EQ(ir->GetBoolean("boolval", false), true); + // skip one section + ASSERT_EQ(ir->ReadSection("string"), true); + // values from different sections + ASSERT_EQ(ir->GetSint32("one", 42), 42); + ASSERT_EQ(ir->GetBoolean("boolval", false), true); + const utf8 * str = ir->GetCString("path", nullptr); + ASSERT_STREQ(str, u8"C:'\\some/dir\\here/神鷹暢遊"); + Memory::Free(str); + // go backa section + ASSERT_EQ(ir->ReadSection("int"), true); + ASSERT_EQ(ir->GetSint32("one", 42), 1); + delete ir; + delete ms; +} + +const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " + "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; diff --git a/test/tests/IniWriterTest.cpp b/test/tests/IniWriterTest.cpp new file mode 100644 index 0000000000..b83a41a1f4 --- /dev/null +++ b/test/tests/IniWriterTest.cpp @@ -0,0 +1,193 @@ +#include +#include +#include "openrct2/config/ConfigEnum.hpp" +#include "openrct2/config/IniWriter.hpp" +#include "openrct2/core/MemoryStream.h" + +class IniWriterTest : public testing::Test +{ +}; + +static auto Enum_Currency = ConfigEnum({ + ConfigEnumEntry("GBP", 1), +}); + +TEST_F(IniWriterTest, create_empty) +{ + MemoryStream * ms = new MemoryStream(0); + ASSERT_NE(ms, nullptr); + ASSERT_EQ(ms->CanRead(), true); + ASSERT_EQ(ms->CanWrite(), true); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_one_section) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteSection("OpenRCT2"); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 12); + ASSERT_EQ(ms->GetLength(), 12); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "[OpenRCT2]\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_multiple_sections) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteSection("OpenRCT1"); + iw->WriteSection("OpenRCT2"); + iw->WriteSection("OpenRCT3"); + iw->WriteSection("OpenRCT4"); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 48); + ASSERT_EQ(ms->GetLength(), 48); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "[OpenRCT1]\n\n[OpenRCT2]\n\n[OpenRCT3]\n\n[OpenRCT4]\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_loose_bool_entry) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteBoolean("boolval", true); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 16); + ASSERT_EQ(ms->GetLength(), 16); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "boolval = true\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_loose_enum_entry) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteEnum("by_string", "stringval"); + iw->WriteEnum("sint32", 0, Enum_Currency); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 34); + ASSERT_EQ(ms->GetLength(), 34); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "by_string = stringval\nsint32 = 0\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_loose_float_entry) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteFloat("one", 1.); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 16); + ASSERT_EQ(ms->GetLength(), 16); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + // This will be non-fatal due to float. + EXPECT_STREQ(ini, "one = 1.000000\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_loose_sint32_entry) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteSint32("one", 1); + iw->WriteSint32("zero", 0); + iw->WriteSint32("minusone", -1); + iw->WriteSint32("intmin", std::numeric_limits::min()); + iw->WriteSint32("intmax", std::numeric_limits::max()); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 73); + ASSERT_EQ(ms->GetLength(), 73); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "one = 1\nzero = 0\nminusone = -1\nintmin = -2147483648\nintmax = 2147483647\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_loose_string_entry) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 43); + ASSERT_EQ(ms->GetLength(), 43); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "path = \"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"); + Memory::Free(ini); + delete iw; + delete ms; +} + +TEST_F(IniWriterTest, create_multiple_section_with_values) +{ + MemoryStream * ms = new MemoryStream(1000); + ASSERT_NE(ms, nullptr); + IIniWriter * iw = CreateIniWriter(ms); + ASSERT_NE(iw, nullptr); + iw->WriteSection("bool"); + iw->WriteBoolean("boolval", true); + iw->WriteSection("int"); + iw->WriteSint32("one", 1); + iw->WriteSint32("zero", 0); + iw->WriteSection("string"); + iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); + int8_t null_terminator = 0; + ms->Write(&null_terminator, 1); + ASSERT_EQ(ms->GetPosition(), 99); + ASSERT_EQ(ms->GetLength(), 99); + ms->SetPosition(0); + const char * ini = (const char *)ms->ReadString(); + ASSERT_STREQ(ini, "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " + "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"); + Memory::Free(ini); + delete iw; + delete ms; +} From e5d569ac6c58cb994e04d966b8c3f62244423e90 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Thu, 23 Feb 2017 23:38:25 +0100 Subject: [PATCH 34/50] Add INI tests to MSVC --- test/tests/tests.vcxproj | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/tests/tests.vcxproj b/test/tests/tests.vcxproj index 5b866801fb..29d46cc6ab 100644 --- a/test/tests/tests.vcxproj +++ b/test/tests/tests.vcxproj @@ -51,6 +51,8 @@ + + From d23edb0f91454dc4acab9bc6ed56806afa3bc3ec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Thu, 23 Feb 2017 23:50:58 +0100 Subject: [PATCH 35/50] Fix INI tests for Windows' 2-byte newlines --- test/tests/IniWriterTest.cpp | 67 +++++++++++++++++++++--------------- 1 file changed, 40 insertions(+), 27 deletions(-) diff --git a/test/tests/IniWriterTest.cpp b/test/tests/IniWriterTest.cpp index b83a41a1f4..58e0e4b9ef 100644 --- a/test/tests/IniWriterTest.cpp +++ b/test/tests/IniWriterTest.cpp @@ -3,6 +3,7 @@ #include "openrct2/config/ConfigEnum.hpp" #include "openrct2/config/IniWriter.hpp" #include "openrct2/core/MemoryStream.h" +#include "openrct2/platform/platform.h" class IniWriterTest : public testing::Test { @@ -33,11 +34,12 @@ TEST_F(IniWriterTest, create_one_section) iw->WriteSection("OpenRCT2"); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 12); - ASSERT_EQ(ms->GetLength(), 12); + ASSERT_GE(ms->GetPosition(), 12); + ASSERT_LE(ms->GetPosition(), 13); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "[OpenRCT2]\n"); + ASSERT_STREQ(ini, "[OpenRCT2]" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -55,11 +57,13 @@ TEST_F(IniWriterTest, create_multiple_sections) iw->WriteSection("OpenRCT4"); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 48); - ASSERT_EQ(ms->GetLength(), 48); + ASSERT_GE(ms->GetPosition(), 48); + ASSERT_LE(ms->GetPosition(), 55); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "[OpenRCT1]\n\n[OpenRCT2]\n\n[OpenRCT3]\n\n[OpenRCT4]\n"); + ASSERT_STREQ(ini, "[OpenRCT1]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[OpenRCT2]" PLATFORM_NEWLINE PLATFORM_NEWLINE + "[OpenRCT3]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[OpenRCT4]" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -74,11 +78,12 @@ TEST_F(IniWriterTest, create_loose_bool_entry) iw->WriteBoolean("boolval", true); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 16); - ASSERT_EQ(ms->GetLength(), 16); + ASSERT_GE(ms->GetPosition(), 16); + ASSERT_LE(ms->GetPosition(), 17); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "boolval = true\n"); + ASSERT_STREQ(ini, "boolval = true" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -94,11 +99,12 @@ TEST_F(IniWriterTest, create_loose_enum_entry) iw->WriteEnum("sint32", 0, Enum_Currency); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 34); - ASSERT_EQ(ms->GetLength(), 34); + ASSERT_GE(ms->GetPosition(), 34); + ASSERT_LE(ms->GetPosition(), 36); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "by_string = stringval\nsint32 = 0\n"); + ASSERT_STREQ(ini, "by_string = stringval" PLATFORM_NEWLINE "sint32 = 0" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -113,12 +119,13 @@ TEST_F(IniWriterTest, create_loose_float_entry) iw->WriteFloat("one", 1.); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 16); - ASSERT_EQ(ms->GetLength(), 16); + ASSERT_GE(ms->GetPosition(), 16); + ASSERT_LE(ms->GetPosition(), 17); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); // This will be non-fatal due to float. - EXPECT_STREQ(ini, "one = 1.000000\n"); + EXPECT_STREQ(ini, "one = 1.000000" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -133,15 +140,17 @@ TEST_F(IniWriterTest, create_loose_sint32_entry) iw->WriteSint32("one", 1); iw->WriteSint32("zero", 0); iw->WriteSint32("minusone", -1); - iw->WriteSint32("intmin", std::numeric_limits::min()); - iw->WriteSint32("intmax", std::numeric_limits::max()); + iw->WriteSint32("intmin", (std::numeric_limits::min)()); + iw->WriteSint32("intmax", (std::numeric_limits::max)()); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 73); - ASSERT_EQ(ms->GetLength(), 73); + ASSERT_GE(ms->GetPosition(), 73); + ASSERT_LE(ms->GetPosition(), 78); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "one = 1\nzero = 0\nminusone = -1\nintmin = -2147483648\nintmax = 2147483647\n"); + ASSERT_STREQ(ini, "one = 1" PLATFORM_NEWLINE "zero = 0" PLATFORM_NEWLINE "minusone = -1" PLATFORM_NEWLINE + "intmin = -2147483648" PLATFORM_NEWLINE "intmax = 2147483647" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -156,11 +165,12 @@ TEST_F(IniWriterTest, create_loose_string_entry) iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 43); - ASSERT_EQ(ms->GetLength(), 43); + ASSERT_GE(ms->GetPosition(), 43); + ASSERT_LE(ms->GetPosition(), 44); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "path = \"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"); + ASSERT_STREQ(ini, "path = \"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; @@ -181,12 +191,15 @@ TEST_F(IniWriterTest, create_multiple_section_with_values) iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); int8_t null_terminator = 0; ms->Write(&null_terminator, 1); - ASSERT_EQ(ms->GetPosition(), 99); - ASSERT_EQ(ms->GetLength(), 99); + ASSERT_GE(ms->GetPosition(), 99); + ASSERT_LE(ms->GetPosition(), 108); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms->GetLength(), ms->GetPosition()); ms->SetPosition(0); const char * ini = (const char *)ms->ReadString(); - ASSERT_STREQ(ini, "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " - "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"); + ASSERT_STREQ(ini, + "[bool]" PLATFORM_NEWLINE "boolval = true" PLATFORM_NEWLINE PLATFORM_NEWLINE "[int]" PLATFORM_NEWLINE + "one = 1" PLATFORM_NEWLINE "zero = 0" PLATFORM_NEWLINE PLATFORM_NEWLINE "[string]" PLATFORM_NEWLINE "path = " + "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; delete ms; From 0a7737489912dd97c23e79b0a6533fbbeb640823 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 19:53:23 +0100 Subject: [PATCH 36/50] Move MemoryStreams in INI tests to stack --- test/tests/IniReaderTest.cpp | 20 ++--- test/tests/IniWriterTest.cpp | 154 ++++++++++++++++------------------- 2 files changed, 76 insertions(+), 98 deletions(-) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 9a8d0740ca..4a1822d58b 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -15,11 +15,10 @@ static auto Enum_Currency = ConfigEnum({}); TEST_F(IniReaderTest, create_empty) { - MemoryStream * ms = new MemoryStream(0); - ASSERT_NE(ms, nullptr); - ASSERT_EQ(ms->CanRead(), true); - ASSERT_EQ(ms->CanWrite(), true); - IIniReader * ir = CreateIniReader(ms); + MemoryStream ms(0); + ASSERT_EQ(ms.CanRead(), true); + ASSERT_EQ(ms.CanWrite(), true); + IIniReader * ir = CreateIniReader(&ms); ASSERT_NE(ir, nullptr); ASSERT_EQ(ir->GetBoolean("nobody", true), true); ASSERT_EQ(ir->GetCString("expects", nullptr), nullptr); @@ -27,16 +26,14 @@ TEST_F(IniReaderTest, create_empty) ASSERT_EQ(ir->GetFloat("inquisition", 1.234f), 1.234f); ASSERT_EQ(ir->GetSint32("universal_answer", 42), 42); delete ir; - delete ms; } TEST_F(IniReaderTest, read_prepared) { - MemoryStream * ms = new MemoryStream(predefined, 99); - ASSERT_NE(ms, nullptr); - ASSERT_EQ(ms->CanRead(), true); - ASSERT_EQ(ms->CanWrite(), false); - IIniReader * ir = CreateIniReader(ms); + MemoryStream ms(predefined, 99); + ASSERT_EQ(ms.CanRead(), true); + ASSERT_EQ(ms.CanWrite(), false); + IIniReader * ir = CreateIniReader(&ms); ASSERT_NE(ir, nullptr); ASSERT_EQ(ir->ReadSection("doesnt_exist"), false); ASSERT_EQ(ir->ReadSection("bool"), true); @@ -59,7 +56,6 @@ TEST_F(IniReaderTest, read_prepared) ASSERT_EQ(ir->ReadSection("int"), true); ASSERT_EQ(ir->GetSint32("one", 42), 1); delete ir; - delete ms; } const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " diff --git a/test/tests/IniWriterTest.cpp b/test/tests/IniWriterTest.cpp index 58e0e4b9ef..d9aa2f12fd 100644 --- a/test/tests/IniWriterTest.cpp +++ b/test/tests/IniWriterTest.cpp @@ -15,127 +15,114 @@ static auto Enum_Currency = ConfigEnum({ TEST_F(IniWriterTest, create_empty) { - MemoryStream * ms = new MemoryStream(0); - ASSERT_NE(ms, nullptr); - ASSERT_EQ(ms->CanRead(), true); - ASSERT_EQ(ms->CanWrite(), true); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(0); + ASSERT_EQ(ms.CanRead(), true); + ASSERT_EQ(ms.CanWrite(), true); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); delete iw; - delete ms; } TEST_F(IniWriterTest, create_one_section) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteSection("OpenRCT2"); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 12); - ASSERT_LE(ms->GetPosition(), 13); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 12); + ASSERT_LE(ms.GetPosition(), 13); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "[OpenRCT2]" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_multiple_sections) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteSection("OpenRCT1"); iw->WriteSection("OpenRCT2"); iw->WriteSection("OpenRCT3"); iw->WriteSection("OpenRCT4"); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 48); - ASSERT_LE(ms->GetPosition(), 55); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 48); + ASSERT_LE(ms.GetPosition(), 55); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "[OpenRCT1]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[OpenRCT2]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[OpenRCT3]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[OpenRCT4]" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_loose_bool_entry) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteBoolean("boolval", true); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 16); - ASSERT_LE(ms->GetPosition(), 17); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 16); + ASSERT_LE(ms.GetPosition(), 17); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "boolval = true" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_loose_enum_entry) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteEnum("by_string", "stringval"); iw->WriteEnum("sint32", 0, Enum_Currency); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 34); - ASSERT_LE(ms->GetPosition(), 36); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 34); + ASSERT_LE(ms.GetPosition(), 36); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "by_string = stringval" PLATFORM_NEWLINE "sint32 = 0" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_loose_float_entry) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteFloat("one", 1.); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 16); - ASSERT_LE(ms->GetPosition(), 17); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 16); + ASSERT_LE(ms.GetPosition(), 17); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); // This will be non-fatal due to float. EXPECT_STREQ(ini, "one = 1.000000" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_loose_sint32_entry) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteSint32("one", 1); iw->WriteSint32("zero", 0); @@ -143,44 +130,40 @@ TEST_F(IniWriterTest, create_loose_sint32_entry) iw->WriteSint32("intmin", (std::numeric_limits::min)()); iw->WriteSint32("intmax", (std::numeric_limits::max)()); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 73); - ASSERT_LE(ms->GetPosition(), 78); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 73); + ASSERT_LE(ms.GetPosition(), 78); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "one = 1" PLATFORM_NEWLINE "zero = 0" PLATFORM_NEWLINE "minusone = -1" PLATFORM_NEWLINE "intmin = -2147483648" PLATFORM_NEWLINE "intmax = 2147483647" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_loose_string_entry) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 43); - ASSERT_LE(ms->GetPosition(), 44); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 43); + ASSERT_LE(ms.GetPosition(), 44); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "path = \"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } TEST_F(IniWriterTest, create_multiple_section_with_values) { - MemoryStream * ms = new MemoryStream(1000); - ASSERT_NE(ms, nullptr); - IIniWriter * iw = CreateIniWriter(ms); + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteSection("bool"); iw->WriteBoolean("boolval", true); @@ -190,17 +173,16 @@ TEST_F(IniWriterTest, create_multiple_section_with_values) iw->WriteSection("string"); iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); int8_t null_terminator = 0; - ms->Write(&null_terminator, 1); - ASSERT_GE(ms->GetPosition(), 99); - ASSERT_LE(ms->GetPosition(), 108); // Accomodate for varying-sized newline (Windows) - ASSERT_EQ(ms->GetLength(), ms->GetPosition()); - ms->SetPosition(0); - const char * ini = (const char *)ms->ReadString(); + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 99); + ASSERT_LE(ms.GetPosition(), 108); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); ASSERT_STREQ(ini, "[bool]" PLATFORM_NEWLINE "boolval = true" PLATFORM_NEWLINE PLATFORM_NEWLINE "[int]" PLATFORM_NEWLINE "one = 1" PLATFORM_NEWLINE "zero = 0" PLATFORM_NEWLINE PLATFORM_NEWLINE "[string]" PLATFORM_NEWLINE "path = " "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"" PLATFORM_NEWLINE); Memory::Free(ini); delete iw; - delete ms; } From 94f0b39f0fd504b181cb6d7607f14bc8386185c2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 20:12:02 +0100 Subject: [PATCH 37/50] Add tests for duplicate sections --- test/tests/IniReaderTest.cpp | 30 +++++++++++++++++++++++++++++- test/tests/IniWriterTest.cpp | 21 +++++++++++++++++++++ 2 files changed, 50 insertions(+), 1 deletion(-) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 4a1822d58b..2b66f8b979 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -9,6 +9,7 @@ class IniReaderTest : public testing::Test { protected: static const utf8 predefined[]; + static const utf8 duplicate[]; }; static auto Enum_Currency = ConfigEnum({}); @@ -52,11 +53,38 @@ TEST_F(IniReaderTest, read_prepared) const utf8 * str = ir->GetCString("path", nullptr); ASSERT_STREQ(str, u8"C:'\\some/dir\\here/神鷹暢遊"); Memory::Free(str); - // go backa section + // go back a section ASSERT_EQ(ir->ReadSection("int"), true); ASSERT_EQ(ir->GetSint32("one", 42), 1); delete ir; } +TEST_F(IniReaderTest, read_duplicate) +{ + MemoryStream ms(duplicate, 99); + ASSERT_EQ(ms.CanRead(), true); + ASSERT_EQ(ms.CanWrite(), false); + IIniReader * ir = CreateIniReader(&ms); + ASSERT_NE(ir, nullptr); + // there should only be data from the last section + ASSERT_EQ(ir->ReadSection("section"), true); + ASSERT_EQ(ir->GetBoolean("one", false), false); + ASSERT_EQ(ir->GetBoolean("two", false), false); + ASSERT_EQ(ir->GetBoolean("three", false), true); + ASSERT_EQ(ir->ReadSection("section"), true); + // try switching to another section + ASSERT_EQ(ir->ReadSection("doesnt_exist"), false); + // make sure we are still in the same section + ASSERT_EQ(ir->GetBoolean("one", false), false); + ASSERT_EQ(ir->GetBoolean("two", false), false); + ASSERT_EQ(ir->GetBoolean("three", false), true); + ASSERT_EQ(ir->ReadSection("section"), true); + // test 4 times, there are only 3 sections + ASSERT_EQ(ir->ReadSection("section"), true); + delete ir; +} + const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; + +const utf8 IniReaderTest::duplicate[] = "[section]\none = true\n[section]\ntwo = true\n[section]\nthree = true\n"; diff --git a/test/tests/IniWriterTest.cpp b/test/tests/IniWriterTest.cpp index d9aa2f12fd..3fc4bc4a03 100644 --- a/test/tests/IniWriterTest.cpp +++ b/test/tests/IniWriterTest.cpp @@ -186,3 +186,24 @@ TEST_F(IniWriterTest, create_multiple_section_with_values) Memory::Free(ini); delete iw; } + +TEST_F(IniWriterTest, create_duplicate_sections) +{ + MemoryStream ms(1000); + IIniWriter * iw = CreateIniWriter(&ms); + ASSERT_NE(iw, nullptr); + iw->WriteSection("section"); + iw->WriteSection("section"); + iw->WriteSection("section"); + int8_t null_terminator = 0; + ms.Write(&null_terminator, 1); + ASSERT_GE(ms.GetPosition(), 33); + ASSERT_LE(ms.GetPosition(), 43); // Accomodate for varying-sized newline (Windows) + ASSERT_EQ(ms.GetLength(), ms.GetPosition()); + ms.SetPosition(0); + const char * ini = (const char *)ms.ReadString(); + ASSERT_STREQ(ini, "[section]" PLATFORM_NEWLINE PLATFORM_NEWLINE "[section]" PLATFORM_NEWLINE PLATFORM_NEWLINE + "[section]" PLATFORM_NEWLINE); + Memory::Free(ini); + delete iw; +} From 21827c91abfe18a42e15242164146d7128dd9ab9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 20:16:22 +0100 Subject: [PATCH 38/50] Extend duplicate INI tests with values --- test/tests/IniReaderTest.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 2b66f8b979..3940e5f503 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -78,6 +78,7 @@ TEST_F(IniReaderTest, read_duplicate) ASSERT_EQ(ir->GetBoolean("one", false), false); ASSERT_EQ(ir->GetBoolean("two", false), false); ASSERT_EQ(ir->GetBoolean("three", false), true); + ASSERT_EQ(ir->GetSint32("fortytwo", 100), 42); ASSERT_EQ(ir->ReadSection("section"), true); // test 4 times, there are only 3 sections ASSERT_EQ(ir->ReadSection("section"), true); @@ -87,4 +88,5 @@ TEST_F(IniReaderTest, read_duplicate) const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; -const utf8 IniReaderTest::duplicate[] = "[section]\none = true\n[section]\ntwo = true\n[section]\nthree = true\n"; +const utf8 IniReaderTest::duplicate[] = + "[section]\none = true\nfortytwo = 13\n[section]\ntwo = true\n[section]\nthree = true\nfortytwo = 42\nfortytwo = 41\n"; From 58da1cde84e6fbc6a3a7ebac912a65311c9d4854 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 20:26:49 +0100 Subject: [PATCH 39/50] Make IniReader not throw while parsing invalid values --- src/openrct2/config/IniReader.cpp | 16 ++++++++++++++-- test/tests/IniReaderTest.cpp | 2 +- 2 files changed, 15 insertions(+), 3 deletions(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index 5a6398f9ac..b42f196a60 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -114,7 +114,13 @@ public: std::string value; if (TryGetString(name, &value)) { - result = std::stoi(value); + try + { + result = std::stoi(value); + } + catch (std::exception) + { + } } return result; } @@ -125,7 +131,13 @@ public: std::string value; if (TryGetString(name, &value)) { - result = std::stof(value); + try + { + result = std::stof(value); + } + catch (std::exception) + { + } } return result; } diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 3940e5f503..432b4520da 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -43,7 +43,7 @@ TEST_F(IniReaderTest, read_prepared) // value from different section ASSERT_EQ(ir->GetSint32("one", 42), 42); // existing value as different type - EXPECT_THROW(ir->GetSint32("boolval", 42), std::invalid_argument); + ASSERT_EQ(ir->GetSint32("boolval", 42), 42); ASSERT_EQ(ir->GetBoolean("boolval", false), true); // skip one section ASSERT_EQ(ir->ReadSection("string"), true); From 84d69b797b7e6f55f7be1b1a6a594f50bbe82d25 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 20:57:36 +0100 Subject: [PATCH 40/50] Change type of variable used in test --- test/tests/IniWriterTest.cpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/test/tests/IniWriterTest.cpp b/test/tests/IniWriterTest.cpp index 3fc4bc4a03..dcfdbe587a 100644 --- a/test/tests/IniWriterTest.cpp +++ b/test/tests/IniWriterTest.cpp @@ -29,7 +29,7 @@ TEST_F(IniWriterTest, create_one_section) IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteSection("OpenRCT2"); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 12); ASSERT_LE(ms.GetPosition(), 13); // Accomodate for varying-sized newline (Windows) @@ -50,7 +50,7 @@ TEST_F(IniWriterTest, create_multiple_sections) iw->WriteSection("OpenRCT2"); iw->WriteSection("OpenRCT3"); iw->WriteSection("OpenRCT4"); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 48); ASSERT_LE(ms.GetPosition(), 55); // Accomodate for varying-sized newline (Windows) @@ -69,7 +69,7 @@ TEST_F(IniWriterTest, create_loose_bool_entry) IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteBoolean("boolval", true); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 16); ASSERT_LE(ms.GetPosition(), 17); // Accomodate for varying-sized newline (Windows) @@ -88,7 +88,7 @@ TEST_F(IniWriterTest, create_loose_enum_entry) ASSERT_NE(iw, nullptr); iw->WriteEnum("by_string", "stringval"); iw->WriteEnum("sint32", 0, Enum_Currency); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 34); ASSERT_LE(ms.GetPosition(), 36); // Accomodate for varying-sized newline (Windows) @@ -106,7 +106,7 @@ TEST_F(IniWriterTest, create_loose_float_entry) IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteFloat("one", 1.); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 16); ASSERT_LE(ms.GetPosition(), 17); // Accomodate for varying-sized newline (Windows) @@ -129,7 +129,7 @@ TEST_F(IniWriterTest, create_loose_sint32_entry) iw->WriteSint32("minusone", -1); iw->WriteSint32("intmin", (std::numeric_limits::min)()); iw->WriteSint32("intmax", (std::numeric_limits::max)()); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 73); ASSERT_LE(ms.GetPosition(), 78); // Accomodate for varying-sized newline (Windows) @@ -148,7 +148,7 @@ TEST_F(IniWriterTest, create_loose_string_entry) IIniWriter * iw = CreateIniWriter(&ms); ASSERT_NE(iw, nullptr); iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 43); ASSERT_LE(ms.GetPosition(), 44); // Accomodate for varying-sized newline (Windows) @@ -172,7 +172,7 @@ TEST_F(IniWriterTest, create_multiple_section_with_values) iw->WriteSint32("zero", 0); iw->WriteSection("string"); iw->WriteString("path", u8"C:'\\some/dir\\here/神鷹暢遊"); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 99); ASSERT_LE(ms.GetPosition(), 108); // Accomodate for varying-sized newline (Windows) @@ -195,7 +195,7 @@ TEST_F(IniWriterTest, create_duplicate_sections) iw->WriteSection("section"); iw->WriteSection("section"); iw->WriteSection("section"); - int8_t null_terminator = 0; + uint8 null_terminator = 0; ms.Write(&null_terminator, 1); ASSERT_GE(ms.GetPosition(), 33); ASSERT_LE(ms.GetPosition(), 43); // Accomodate for varying-sized newline (Windows) From 3b341de8357a31decae27b84b98e442cc954dbca Mon Sep 17 00:00:00 2001 From: Ted John Date: Fri, 24 Feb 2017 21:48:06 +0000 Subject: [PATCH 41/50] Fix String::Trim and add test --- src/openrct2/core/String.cpp | 27 ++++++++++----------------- test/tests/StringTest.cpp | 27 +++++++++++++++++++++++++++ test/tests/tests.vcxproj | 3 +-- 3 files changed, 38 insertions(+), 19 deletions(-) create mode 100644 test/tests/StringTest.cpp diff --git a/src/openrct2/core/String.cpp b/src/openrct2/core/String.cpp index 6921dc3eca..5f3fafd435 100644 --- a/src/openrct2/core/String.cpp +++ b/src/openrct2/core/String.cpp @@ -399,36 +399,29 @@ namespace String codepoint_t codepoint; const utf8 * ch = s.c_str(); const utf8 * nextCh; - const utf8 * firstNonWhitespace = nullptr; - const utf8 * lastNonWhitespace = nullptr; + const utf8 * startSubstr = nullptr; + const utf8 * endSubstr = nullptr; while ((codepoint = GetNextCodepoint(ch, &nextCh)) != '\0') { bool isWhiteSpace = codepoint <= WCHAR_MAX && iswspace((wchar_t)codepoint); if (!isWhiteSpace) { - if (firstNonWhitespace == nullptr) + if (startSubstr == nullptr) { - firstNonWhitespace = ch; + startSubstr = ch; } - lastNonWhitespace = ch; + endSubstr = ch; } ch = nextCh; } - if (firstNonWhitespace != nullptr && - firstNonWhitespace != s.c_str()) - { - size_t newStringSize = ch - firstNonWhitespace; - return std::string(firstNonWhitespace, newStringSize); - } - else if (lastNonWhitespace != nullptr) - { - size_t newStringSize = lastNonWhitespace - s.c_str() + 1; - return std::string(s.c_str(), newStringSize); - } - else + if (startSubstr == nullptr) { + // String is all whitespace return std::string(); } + + size_t stringLength = endSubstr - startSubstr + 1; + return std::string(startSubstr, stringLength); } } diff --git a/test/tests/StringTest.cpp b/test/tests/StringTest.cpp new file mode 100644 index 0000000000..46c4bb8be9 --- /dev/null +++ b/test/tests/StringTest.cpp @@ -0,0 +1,27 @@ +#include +#include +#include +#include + +using TCase = std::tuple; + +class StringTest : public testing::TestWithParam +{ +}; + +INSTANTIATE_TEST_CASE_P(TrimData, StringTest, testing::Values( + TCase("string", "string"), + TCase(" string", "string"), + TCase("string ", "string"), + TCase(" some string ", "some string"), + TCase(" ", ""), + TCase("", "") +)); +TEST_P(StringTest, Trim) +{ + auto testCase = GetParam(); + std::string input = std::get<0>(testCase); + std::string expected = std::get<1>(testCase); + std::string actual = String::Trim(input); + ASSERT_EQ(expected, actual); +} diff --git a/test/tests/tests.vcxproj b/test/tests/tests.vcxproj index 29d46cc6ab..02dc0344b5 100644 --- a/test/tests/tests.vcxproj +++ b/test/tests/tests.vcxproj @@ -45,7 +45,6 @@ Console - @@ -56,7 +55,7 @@ + - \ No newline at end of file From d41293fa6b9075c11aab8f99248996cbc94ec801 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 23:04:20 +0100 Subject: [PATCH 42/50] Extract common test sources into library --- test/tests/CMakeLists.txt | 41 ++++++++++++++++++--------------------- 1 file changed, 19 insertions(+), 22 deletions(-) diff --git a/test/tests/CMakeLists.txt b/test/tests/CMakeLists.txt index 6dcf7cb79a..058a2bdbe4 100644 --- a/test/tests/CMakeLists.txt +++ b/test/tests/CMakeLists.txt @@ -55,6 +55,22 @@ include_directories("../../src") set(GTEST_LIBRARIES gtest gtest_main pthread) +# Some most common files required in tests +set(COMMON_TEST_SOURCES + "../../src/openrct2/core/Console.cpp" + "../../src/openrct2/core/Diagnostics.cpp" + "../../src/openrct2/core/Guard.cpp" + "../../src/openrct2/core/String.cpp" + "../../src/openrct2/diagnostic.c" + "../../src/openrct2/localisation/format_codes.c" + "../../src/openrct2/localisation/utf8.c" + "../../src/openrct2/util/util.c" + "../../src/openrct2/Version.cpp" + ) + +# Create a re-usable library to save some compilation time +add_library(test-common STATIC ${COMMON_TEST_SOURCES}) + # Start of our tests # sawyercoding test @@ -73,39 +89,20 @@ add_test(NAME sawyercoding COMMAND test_sawyercoding) set(LANGUAGEPACK_TEST_SOURCES "LanguagePackTest.cpp" "../../src/openrct2/localisation/LanguagePack.cpp" - "../../src/openrct2/core/Console.cpp" - "../../src/openrct2/core/Diagnostics.cpp" - "../../src/openrct2/core/Guard.cpp" - "../../src/openrct2/core/String.cpp" - "../../src/openrct2/diagnostic.c" - "../../src/openrct2/localisation/format_codes.c" - "../../src/openrct2/localisation/utf8.c" - "../../src/openrct2/util/util.c" - "../../src/openrct2/Version.cpp" ) add_executable(test_languagepack ${LANGUAGEPACK_TEST_SOURCES}) -target_link_libraries(test_languagepack ${GTEST_LIBRARIES} dl z SDL2 SDL2_ttf ssl crypto) +target_link_libraries(test_languagepack ${GTEST_LIBRARIES} test-common dl z SDL2 SDL2_ttf ssl crypto) add_test(NAME languagepack COMMAND test_languagepack) - -# LanguagePack test +# INI test set(INI_TEST_SOURCES "IniWriterTest.cpp" "IniReaderTest.cpp" "../../src/openrct2/config/IniReader.cpp" "../../src/openrct2/config/IniWriter.cpp" - "../../src/openrct2/core/Console.cpp" - "../../src/openrct2/core/Diagnostics.cpp" - "../../src/openrct2/core/Guard.cpp" "../../src/openrct2/core/IStream.cpp" "../../src/openrct2/core/MemoryStream.cpp" - "../../src/openrct2/core/String.cpp" - "../../src/openrct2/diagnostic.c" - "../../src/openrct2/localisation/format_codes.c" - "../../src/openrct2/localisation/utf8.c" - "../../src/openrct2/util/util.c" - "../../src/openrct2/Version.cpp" ) add_executable(test_ini ${INI_TEST_SOURCES}) -target_link_libraries(test_ini ${GTEST_LIBRARIES} dl z) +target_link_libraries(test_ini ${GTEST_LIBRARIES} test-common dl z) add_test(NAME ini COMMAND test_ini) From 5f43c37ca0deb33bde0c831cc4d9616bafc2ae87 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 23:04:36 +0100 Subject: [PATCH 43/50] Add String test to CMake --- test/tests/CMakeLists.txt | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/test/tests/CMakeLists.txt b/test/tests/CMakeLists.txt index 058a2bdbe4..f1e2890ee9 100644 --- a/test/tests/CMakeLists.txt +++ b/test/tests/CMakeLists.txt @@ -106,3 +106,11 @@ set(INI_TEST_SOURCES add_executable(test_ini ${INI_TEST_SOURCES}) target_link_libraries(test_ini ${GTEST_LIBRARIES} test-common dl z) add_test(NAME ini COMMAND test_ini) + +# String test +set(STRING_TEST_SOURCES + "StringTest.cpp" + ) +add_executable(test_string ${STRING_TEST_SOURCES}) +target_link_libraries(test_string ${GTEST_LIBRARIES} test-common dl z) +add_test(NAME string COMMAND test_string) From 3b3f0b2e6b8b4ebf464408aa7b57817116da01c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 23:23:20 +0100 Subject: [PATCH 44/50] Return actual instead of default value in IniReader::GetString --- src/openrct2/config/IniReader.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/openrct2/config/IniReader.cpp b/src/openrct2/config/IniReader.cpp index b42f196a60..4f0e67ed9c 100644 --- a/src/openrct2/config/IniReader.cpp +++ b/src/openrct2/config/IniReader.cpp @@ -145,7 +145,7 @@ public: std::string GetString(const std::string &name, const std::string &defaultValue) const override { std::string result; - if (TryGetString(name, &result)) + if (!TryGetString(name, &result)) { result = defaultValue; } From 7d0cc839088454f80f0093b4e6d1ed6a4e081c15 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Fri, 24 Feb 2017 22:12:17 +0100 Subject: [PATCH 45/50] Add tests for untrimmed INI --- test/tests/IniReaderTest.cpp | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 432b4520da..62ac577cdf 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -10,6 +10,7 @@ class IniReaderTest : public testing::Test protected: static const utf8 predefined[]; static const utf8 duplicate[]; + static const utf8 untrimmed[]; }; static auto Enum_Currency = ConfigEnum({}); @@ -85,8 +86,28 @@ TEST_F(IniReaderTest, read_duplicate) delete ir; } +TEST_F(IniReaderTest, read_untrimmed) +{ + MemoryStream ms(untrimmed, 99); + ASSERT_EQ(ms.CanRead(), true); + ASSERT_EQ(ms.CanWrite(), false); + IIniReader * ir = CreateIniReader(&ms); + ASSERT_NE(ir, nullptr); + // there should only be data from the last section + ASSERT_EQ(ir->ReadSection("section"), true); + ASSERT_EQ(ir->GetBoolean("one", false), true); + const utf8 * str = ir->GetCString("str", nullptr); + ASSERT_STREQ(str, " xxx "); + Memory::Free(str); + ASSERT_EQ(ir->GetString("str", "yyy"), " xxx "); + ASSERT_EQ(ir->GetString("nosuchthing", " yyy "), " yyy "); + delete ir; +} + const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; const utf8 IniReaderTest::duplicate[] = "[section]\none = true\nfortytwo = 13\n[section]\ntwo = true\n[section]\nthree = true\nfortytwo = 42\nfortytwo = 41\n"; + +const utf8 IniReaderTest::untrimmed[] = "[section]\n one = true \n str = \" xxx \""; From fe2cb79d18d1f82685b1e1d6866656cd2a21bb74 Mon Sep 17 00:00:00 2001 From: Ted John Date: Fri, 24 Feb 2017 22:57:32 +0000 Subject: [PATCH 46/50] Use strings for test data in IniReaderTest --- test/tests/IniReaderTest.cpp | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 62ac577cdf..92090401d9 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -8,9 +8,9 @@ class IniReaderTest : public testing::Test { protected: - static const utf8 predefined[]; - static const utf8 duplicate[]; - static const utf8 untrimmed[]; + static const std::string predefined; + static const std::string duplicate; + static const std::string untrimmed; }; static auto Enum_Currency = ConfigEnum({}); @@ -32,7 +32,7 @@ TEST_F(IniReaderTest, create_empty) TEST_F(IniReaderTest, read_prepared) { - MemoryStream ms(predefined, 99); + MemoryStream ms(predefined.c_str(), predefined.size()); ASSERT_EQ(ms.CanRead(), true); ASSERT_EQ(ms.CanWrite(), false); IIniReader * ir = CreateIniReader(&ms); @@ -62,7 +62,7 @@ TEST_F(IniReaderTest, read_prepared) TEST_F(IniReaderTest, read_duplicate) { - MemoryStream ms(duplicate, 99); + MemoryStream ms(duplicate.c_str(), duplicate.size()); ASSERT_EQ(ms.CanRead(), true); ASSERT_EQ(ms.CanWrite(), false); IIniReader * ir = CreateIniReader(&ms); @@ -88,7 +88,7 @@ TEST_F(IniReaderTest, read_duplicate) TEST_F(IniReaderTest, read_untrimmed) { - MemoryStream ms(untrimmed, 99); + MemoryStream ms(untrimmed.c_str(), untrimmed.size()); ASSERT_EQ(ms.CanRead(), true); ASSERT_EQ(ms.CanWrite(), false); IIniReader * ir = CreateIniReader(&ms); @@ -104,10 +104,10 @@ TEST_F(IniReaderTest, read_untrimmed) delete ir; } -const utf8 IniReaderTest::predefined[] = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " +const std::string IniReaderTest::predefined = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; -const utf8 IniReaderTest::duplicate[] = +const std::string IniReaderTest::duplicate = "[section]\none = true\nfortytwo = 13\n[section]\ntwo = true\n[section]\nthree = true\nfortytwo = 42\nfortytwo = 41\n"; -const utf8 IniReaderTest::untrimmed[] = "[section]\n one = true \n str = \" xxx \""; +const std::string IniReaderTest::untrimmed = "[section]\n one = true \n str = \" xxx \""; From f851198645a2cdef86e85e598e7e0ec16834ca57 Mon Sep 17 00:00:00 2001 From: Ted John Date: Fri, 24 Feb 2017 23:00:27 +0000 Subject: [PATCH 47/50] Fix and format test data --- test/tests/IniReaderTest.cpp | 28 +++++++++++++++++++++++----- 1 file changed, 23 insertions(+), 5 deletions(-) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 92090401d9..12e374ffc5 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -79,7 +79,7 @@ TEST_F(IniReaderTest, read_duplicate) ASSERT_EQ(ir->GetBoolean("one", false), false); ASSERT_EQ(ir->GetBoolean("two", false), false); ASSERT_EQ(ir->GetBoolean("three", false), true); - ASSERT_EQ(ir->GetSint32("fortytwo", 100), 42); + ASSERT_EQ(ir->GetSint32("fortytwo", 100), 41); ASSERT_EQ(ir->ReadSection("section"), true); // test 4 times, there are only 3 sections ASSERT_EQ(ir->ReadSection("section"), true); @@ -104,10 +104,28 @@ TEST_F(IniReaderTest, read_untrimmed) delete ir; } -const std::string IniReaderTest::predefined = "[bool]\nboolval = true\n\n[int]\none = 1\nzero = 0\n\n[string]\npath = " - "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; +const std::string IniReaderTest::predefined = + "[bool]\n" + "boolval = true\n\n" + "[int]\n" + "one = 1\n" + "zero = 0\n\n" + "[string]\n" + "path = " + "\"C:'\\\\some/dir\\\\here/\xE7\xA5\x9E\xE9\xB7\xB9\xE6\x9A\xA2\xE9\x81\x8A\"\n"; const std::string IniReaderTest::duplicate = - "[section]\none = true\nfortytwo = 13\n[section]\ntwo = true\n[section]\nthree = true\nfortytwo = 42\nfortytwo = 41\n"; + "[section]\n" + "one = true\n" + "fortytwo = 13\n" + "[section]\n" + "two = true\n" + "[section]\n" + "three = true\n" + "fortytwo = 42\n" + "fortytwo = 41\n"; -const std::string IniReaderTest::untrimmed = "[section]\n one = true \n str = \" xxx \""; +const std::string IniReaderTest::untrimmed = + "[section]\n" + "one = true \n" + " str = \" xxx \""; From 62ab0e0e030600300e43e95cbbe0a5ad2b79d432 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Sat, 25 Feb 2017 00:06:58 +0100 Subject: [PATCH 48/50] Add missing include to IniReaderTest --- test/tests/IniReaderTest.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/test/tests/IniReaderTest.cpp b/test/tests/IniReaderTest.cpp index 12e374ffc5..05c1c73b5a 100644 --- a/test/tests/IniReaderTest.cpp +++ b/test/tests/IniReaderTest.cpp @@ -1,5 +1,6 @@ #include #include +#include #include "openrct2/config/ConfigEnum.hpp" #include "openrct2/config/IniReader.hpp" #include "openrct2/core/MemoryStream.h" From e39444b592603e65156f3574fd0bae65477e8f79 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Sat, 25 Feb 2017 00:07:19 +0100 Subject: [PATCH 49/50] Add more test cases to StringTest --- test/tests/StringTest.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/test/tests/StringTest.cpp b/test/tests/StringTest.cpp index 46c4bb8be9..8644c3c19b 100644 --- a/test/tests/StringTest.cpp +++ b/test/tests/StringTest.cpp @@ -15,7 +15,10 @@ INSTANTIATE_TEST_CASE_P(TrimData, StringTest, testing::Values( TCase("string ", "string"), TCase(" some string ", "some string"), TCase(" ", ""), - TCase("", "") + TCase("", ""), + TCase("\n", ""), + TCase("\n\n\n\r\n", ""), + TCase("\n\n\n\r\nstring\n\n", "string") )); TEST_P(StringTest, Trim) { From d610ef54477ed3072400261077968bebdda9b941 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C5=82=20Janiszewski?= Date: Sat, 25 Feb 2017 00:10:27 +0100 Subject: [PATCH 50/50] Remove unnecessary libs from linking to tests [ci skip] --- test/tests/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/tests/CMakeLists.txt b/test/tests/CMakeLists.txt index f1e2890ee9..763fa706f7 100644 --- a/test/tests/CMakeLists.txt +++ b/test/tests/CMakeLists.txt @@ -91,7 +91,7 @@ set(LANGUAGEPACK_TEST_SOURCES "../../src/openrct2/localisation/LanguagePack.cpp" ) add_executable(test_languagepack ${LANGUAGEPACK_TEST_SOURCES}) -target_link_libraries(test_languagepack ${GTEST_LIBRARIES} test-common dl z SDL2 SDL2_ttf ssl crypto) +target_link_libraries(test_languagepack ${GTEST_LIBRARIES} test-common dl z SDL2) add_test(NAME languagepack COMMAND test_languagepack) # INI test