[MMIXER] Fix additional data size initialization for different audio formats (#6753)
[reactos.git] / base / applications / rapps / settings.cpp
1 /*
2 * PROJECT: ReactOS Applications Manager
3 * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4 * PURPOSE: Functions to load / save settings from reg.
5 * COPYRIGHT: Copyright 2020 He Yang (1160386205@qq.com)
6 */
7
8 #include "rapps.h"
9 #include "settings.h"
10
11
12 class SettingsField
13 {
14 public:
15 virtual ~SettingsField() { ; }
16 virtual BOOL Save(CRegKey &key) = 0;
17 virtual BOOL Load(CRegKey &key) = 0;
18 };
19
20 class SettingsFieldBool : public SettingsField
21 {
22 public:
23 SettingsFieldBool(BOOL *pValue, LPCWSTR szRegName)
24 : m_pValueStore(pValue), m_RegName(szRegName)
25 {
26 }
27
28 virtual BOOL Save(CRegKey &key) override
29 {
30 return key.SetDWORDValue(m_RegName, (DWORD)(*m_pValueStore)) == ERROR_SUCCESS;
31 }
32 virtual BOOL Load(CRegKey &key) override
33 {
34 DWORD dwField;
35 LONG lResult = key.QueryDWORDValue(m_RegName, dwField);
36 if (lResult != ERROR_SUCCESS)
37 {
38 return FALSE;
39 }
40 *m_pValueStore = (BOOL)dwField;
41 return TRUE;
42 }
43
44 private:
45 BOOL *m_pValueStore; // where to read/store the value
46 LPCWSTR m_RegName; // key name in registery
47 };
48
49 class SettingsFieldInt : public SettingsField
50 {
51 public:
52 SettingsFieldInt(INT *pValue, LPCWSTR szRegName)
53 : m_pValueStore(pValue), m_RegName(szRegName)
54 {
55 }
56
57 virtual BOOL Save(CRegKey &key) override
58 {
59 return key.SetDWORDValue(m_RegName, (DWORD)(*m_pValueStore)) == ERROR_SUCCESS;
60 }
61 virtual BOOL Load(CRegKey &key) override
62 {
63 DWORD dwField;
64 LONG lResult = key.QueryDWORDValue(m_RegName, dwField);
65 if (lResult != ERROR_SUCCESS)
66 {
67 return FALSE;
68 }
69 *m_pValueStore = (INT)dwField;
70 return TRUE;
71 }
72
73 private:
74 INT *m_pValueStore; // where to read/store the value
75 LPCWSTR m_RegName; // key name in registery
76 };
77
78 class SettingsFieldString : public SettingsField
79 {
80 public:
81 SettingsFieldString(WCHAR *pString, ULONG cchLen, LPCWSTR szRegName)
82 : m_pStringStore(pString), m_StringLen(cchLen), m_RegName(szRegName)
83 {
84 }
85
86 virtual BOOL Save(CRegKey &key) override
87 {
88 return key.SetStringValue(m_RegName, m_pStringStore) == ERROR_SUCCESS;
89 }
90 virtual BOOL Load(CRegKey &key) override
91 {
92 ULONG nChar = m_StringLen - 1; // make sure the terminating L'\0'
93 LONG lResult = key.QueryStringValue(m_RegName, m_pStringStore, &nChar);
94 return lResult == ERROR_SUCCESS;
95 }
96
97 private:
98 WCHAR *m_pStringStore; // where to read/store the value
99 ULONG m_StringLen; // string length, in chars
100 LPCWSTR m_RegName; // key name in registery
101 };
102
103
104 void AddInfoFields(ATL::CAtlList<SettingsField *> &infoFields, SETTINGS_INFO &settings)
105 {
106 infoFields.AddTail(new SettingsFieldBool(&(settings.bSaveWndPos), L"bSaveWndPos"));
107 infoFields.AddTail(new SettingsFieldBool(&(settings.bUpdateAtStart), L"bUpdateAtStart"));
108 infoFields.AddTail(new SettingsFieldBool(&(settings.bLogEnabled), L"bLogEnabled"));
109 infoFields.AddTail(new SettingsFieldString(settings.szDownloadDir, MAX_PATH, L"szDownloadDir"));
110 infoFields.AddTail(new SettingsFieldBool(&(settings.bDelInstaller), L"bDelInstaller"));
111 infoFields.AddTail(new SettingsFieldBool(&(settings.Maximized), L"WindowPosMaximized"));
112 infoFields.AddTail(new SettingsFieldInt(&(settings.Left), L"WindowPosLeft"));
113 infoFields.AddTail(new SettingsFieldInt(&(settings.Top), L"WindowPosTop"));
114 infoFields.AddTail(new SettingsFieldInt(&(settings.Width), L"WindowPosWidth"));
115 infoFields.AddTail(new SettingsFieldInt(&(settings.Height), L"WindowPosHeight"));
116 infoFields.AddTail(new SettingsFieldInt(&(settings.Proxy), L"ProxyMode"));
117 infoFields.AddTail(new SettingsFieldString((settings.szProxyServer), MAX_PATH, L"ProxyServer"));
118 infoFields.AddTail(new SettingsFieldString((settings.szNoProxyFor), MAX_PATH, L"NoProxyFor"));
119 infoFields.AddTail(new SettingsFieldBool(&(settings.bUseSource), L"bUseSource"));
120 infoFields.AddTail(new SettingsFieldString((settings.szSourceURL), INTERNET_MAX_URL_LENGTH, L"SourceURL"));
121
122 return;
123 }
124
125 BOOL SaveAllSettings(CRegKey &key, SETTINGS_INFO &settings)
126 {
127 BOOL bAllSuccess = TRUE;
128 ATL::CAtlList<SettingsField *> infoFields;
129
130 AddInfoFields(infoFields, settings);
131
132 POSITION InfoListPosition = infoFields.GetHeadPosition();
133 while (InfoListPosition)
134 {
135 SettingsField *Info = infoFields.GetNext(InfoListPosition);
136 if (!Info->Save(key))
137 {
138 bAllSuccess = FALSE;
139 // TODO: error log
140 }
141 delete Info;
142 }
143 return bAllSuccess;
144 }
145
146 BOOL LoadAllSettings(CRegKey &key, SETTINGS_INFO &settings)
147 {
148 BOOL bAllSuccess = TRUE;
149 ATL::CAtlList<SettingsField *> infoFields;
150
151 AddInfoFields(infoFields, settings);
152
153 POSITION InfoListPosition = infoFields.GetHeadPosition();
154 while (InfoListPosition)
155 {
156 SettingsField *Info = infoFields.GetNext(InfoListPosition);
157 if (!Info->Load(key))
158 {
159 bAllSuccess = FALSE;
160 // TODO: error log
161 }
162 delete Info;
163 }
164 return bAllSuccess;
165 }
166
167 VOID FillDefaultSettings(PSETTINGS_INFO pSettingsInfo)
168 {
169 ATL::CStringW szDownloadDir;
170 ZeroMemory(pSettingsInfo, sizeof(SETTINGS_INFO));
171
172 pSettingsInfo->bSaveWndPos = TRUE;
173 pSettingsInfo->bUpdateAtStart = FALSE;
174 pSettingsInfo->bLogEnabled = TRUE;
175 pSettingsInfo->bUseSource = FALSE;
176
177 if (FAILED(SHGetFolderPathW(NULL, CSIDL_PERSONAL, NULL, SHGFP_TYPE_CURRENT, szDownloadDir.GetBuffer(MAX_PATH))))
178 {
179 szDownloadDir.ReleaseBuffer();
180 if (!szDownloadDir.GetEnvironmentVariableW(L"SystemDrive"))
181 {
182 szDownloadDir = L"C:";
183 }
184 }
185 else
186 {
187 szDownloadDir.ReleaseBuffer();
188 }
189
190 PathAppendW(szDownloadDir.GetBuffer(MAX_PATH), L"\\RAPPS Downloads");
191 szDownloadDir.ReleaseBuffer();
192
193 ATL::CStringW::CopyChars(pSettingsInfo->szDownloadDir,
194 _countof(pSettingsInfo->szDownloadDir),
195 szDownloadDir.GetString(),
196 szDownloadDir.GetLength() + 1);
197
198 pSettingsInfo->bDelInstaller = FALSE;
199 pSettingsInfo->Maximized = FALSE;
200 pSettingsInfo->Left = CW_USEDEFAULT;
201 pSettingsInfo->Top = CW_USEDEFAULT;
202 pSettingsInfo->Width = 680;
203 pSettingsInfo->Height = 450;
204 }
205
206 BOOL LoadSettings(PSETTINGS_INFO pSettingsInfo)
207 {
208 ATL::CRegKey RegKey;
209 if (RegKey.Open(HKEY_CURRENT_USER, L"Software\\ReactOS\\rapps", KEY_READ) != ERROR_SUCCESS)
210 {
211 return FALSE;
212 }
213
214 return LoadAllSettings(RegKey, *pSettingsInfo);
215 }
216
217 BOOL SaveSettings(HWND hwnd, PSETTINGS_INFO pSettingsInfo)
218 {
219 WINDOWPLACEMENT wp;
220 ATL::CRegKey RegKey;
221
222 if (pSettingsInfo->bSaveWndPos)
223 {
224 wp.length = sizeof(wp);
225 GetWindowPlacement(hwnd, &wp);
226
227 pSettingsInfo->Left = wp.rcNormalPosition.left;
228 pSettingsInfo->Top = wp.rcNormalPosition.top;
229 pSettingsInfo->Width = wp.rcNormalPosition.right - wp.rcNormalPosition.left;
230 pSettingsInfo->Height = wp.rcNormalPosition.bottom - wp.rcNormalPosition.top;
231 pSettingsInfo->Maximized = (wp.showCmd == SW_MAXIMIZE
232 || (wp.showCmd == SW_SHOWMINIMIZED
233 && (wp.flags & WPF_RESTORETOMAXIMIZED)));
234 }
235
236 if (RegKey.Create(HKEY_CURRENT_USER, L"Software\\ReactOS\\rapps", NULL,
237 REG_OPTION_NON_VOLATILE, KEY_WRITE, NULL, NULL) != ERROR_SUCCESS)
238 {
239 return FALSE;
240 }
241
242 return SaveAllSettings(RegKey, *pSettingsInfo);
243 }