Changeset View
Changeset View
Standalone View
Standalone View
source/ps/ConfigDB.h
Show First 20 Lines • Show All 48 Lines • ▼ Show 20 Lines | enum EConfigNamespace | ||||
CFG_HWDETECT, | CFG_HWDETECT, | ||||
CFG_USER, | CFG_USER, | ||||
CFG_COMMAND, | CFG_COMMAND, | ||||
CFG_LAST | CFG_LAST | ||||
}; | }; | ||||
using CConfigValueSet = std::vector<CStr>; | using CConfigValueSet = std::vector<CStr>; | ||||
// Opaque data type so that callers that hook into ConfigDB can delete their hooks. | |||||
// Would be defined in CConfigDB but then it couldn't be forward-declared, which is rather annoying. | |||||
// Actually defined below - requires access to CConfigDB. | |||||
class CConfigDBHook; | |||||
#define g_ConfigDB CConfigDB::GetSingleton() | #define g_ConfigDB CConfigDB::GetSingleton() | ||||
class CConfigDB : public Singleton<CConfigDB> | class CConfigDB : public Singleton<CConfigDB> | ||||
{ | { | ||||
friend CConfigDBHook; | |||||
public: | public: | ||||
/** | /** | ||||
* Attempt to retrieve the value of a config variable with the given name; | * Attempt to retrieve the value of a config variable with the given name; | ||||
* will search CFG_COMMAND first, and then all namespaces from the specified | * will search CFG_COMMAND first, and then all namespaces from the specified | ||||
* namespace down. | * namespace down. | ||||
*/ | */ | ||||
void GetValue(EConfigNamespace ns, const CStr& name, bool& value); | void GetValue(EConfigNamespace ns, const CStr& name, bool& value); | ||||
///@copydoc CConfigDB::GetValue | ///@copydoc CConfigDB::GetValue | ||||
▲ Show 20 Lines • Show All 94 Lines • ▼ Show 20 Lines | public: | ||||
* Returns: | * Returns: | ||||
* true: if the config value was successfully saved and written to the file | * true: if the config value was successfully saved and written to the file | ||||
* false: if an error occurred | * false: if an error occurred | ||||
*/ | */ | ||||
bool WriteValueToFile(EConfigNamespace ns, const CStr& name, const CStr& value, const VfsPath& path); | bool WriteValueToFile(EConfigNamespace ns, const CStr& name, const CStr& value, const VfsPath& path); | ||||
bool WriteValueToFile(EConfigNamespace ns, const CStr& name, const CStr& value); | bool WriteValueToFile(EConfigNamespace ns, const CStr& name, const CStr& value); | ||||
// Opaque data type so that callers that hook into ConfigDB can delete their hooks. | |||||
class hook_t | |||||
{ | |||||
friend class CConfigDB; | |||||
public: | |||||
// Point the moved-from hook to end, which is checked for in UnregisterHook, | |||||
// to avoid a double-erase error. | |||||
hook_t(hook_t&& h) { ptr = std::move(h.ptr); h.ptr = m_Hooks.end(); } | |||||
hook_t(const hook_t&) = delete; | |||||
private: | |||||
hook_t(std::multimap<CStr, std::function<void()>>::iterator p) : ptr(p) {}; | |||||
std::multimap<CStr, std::function<void()>>::iterator ptr; | |||||
}; | |||||
/** | /** | ||||
* Register a simple lambda that will be called anytime the value changes in any namespace | * Register a simple lambda that will be called anytime the value changes in any namespace | ||||
* This is simple on purpose, the hook is responsible for checking if it should do something. | * This is simple on purpose, the hook is responsible for checking if it should do something. | ||||
* When RegisterHookAndCall is called, the hook is immediately triggered. | * When RegisterHookAndCall is called, the hook is immediately triggered. | ||||
*/ | */ | ||||
hook_t RegisterHookAndCall(const CStr& name, std::function<void()> hook); | CConfigDBHook RegisterHookAndCall(const CStr& name, std::function<void()> hook); | ||||
void UnregisterHook(hook_t&& hook); | void UnregisterHook(CConfigDBHook&& hook); | ||||
void UnregisterHook(std::unique_ptr<CConfigDBHook>&& hook); | |||||
private: | private: | ||||
static std::map<CStr, CConfigValueSet> m_Map[]; | static std::map<CStr, CConfigValueSet> m_Map[]; | ||||
static std::multimap<CStr, std::function<void()>> m_Hooks; | static std::multimap<CStr, std::function<void()>> m_Hooks; | ||||
static VfsPath m_ConfigFile[]; | static VfsPath m_ConfigFile[]; | ||||
static bool m_HasChanges[]; | static bool m_HasChanges[]; | ||||
}; | }; | ||||
class CConfigDBHook | |||||
{ | |||||
friend class CConfigDB; | |||||
public: | |||||
CConfigDBHook() = delete; | |||||
// Point the moved-from hook to end, which is checked for in UnregisterHook, | |||||
// to avoid a double-erase error. | |||||
CConfigDBHook(CConfigDBHook&& h) : configDB(h.configDB) { ptr = std::move(h.ptr); h.ptr = configDB.m_Hooks.end(); } | |||||
CConfigDBHook(const CConfigDBHook&) = delete; | |||||
private: | |||||
CConfigDBHook(CConfigDB& cdb, std::multimap<CStr, std::function<void()>>::iterator p) : configDB(cdb), ptr(p) {}; | |||||
std::multimap<CStr, std::function<void()>>::iterator ptr; | |||||
CConfigDB& configDB; | |||||
}; | |||||
// stores the value of the given key into <destination>. this quasi-template | // stores the value of the given key into <destination>. this quasi-template | ||||
// convenience wrapper on top of GetValue simplifies user code | // convenience wrapper on top of GetValue simplifies user code | ||||
#define CFG_GET_VAL(name, destination)\ | #define CFG_GET_VAL(name, destination)\ | ||||
g_ConfigDB.GetValue(CFG_USER, name, destination) | g_ConfigDB.GetValue(CFG_USER, name, destination) | ||||
#endif // INCLUDED_CONFIGDB | #endif // INCLUDED_CONFIGDB |
Wildfire Games · Phabricator