xref: /aosp_15_r20/external/lzma/CPP/7zip/UI/FileManager/ViewSettings.cpp (revision f6dc9357d832569d4d1f5d24eacdb3935a1ae8e6)
1 // ViewSettings.cpp
2 
3 #include "StdAfx.h"
4 
5 #include "../../../../C/CpuArch.h"
6 
7 #include "../../../Common/IntToString.h"
8 #include "../../../Common/StringConvert.h"
9 
10 #include "../../../Windows/Registry.h"
11 #include "../../../Windows/Synchronization.h"
12 
13 #include "ViewSettings.h"
14 
15 using namespace NWindows;
16 using namespace NRegistry;
17 
18 #define REG_PATH_FM TEXT("Software") TEXT(STRING_PATH_SEPARATOR) TEXT("7-Zip") TEXT(STRING_PATH_SEPARATOR) TEXT("FM")
19 
20 static LPCTSTR const kCUBasePath = REG_PATH_FM;
21 static LPCTSTR const kCulumnsKeyName = REG_PATH_FM TEXT(STRING_PATH_SEPARATOR) TEXT("Columns");
22 
23 static LPCTSTR const kPositionValueName = TEXT("Position");
24 static LPCTSTR const kPanelsInfoValueName = TEXT("Panels");
25 static LPCTSTR const kToolbars = TEXT("Toolbars");
26 
27 static LPCWSTR const kPanelPathValueName = L"PanelPath";
28 
29 static LPCTSTR const kListMode = TEXT("ListMode");
30 static LPCTSTR const kFolderHistoryValueName = TEXT("FolderHistory");
31 static LPCTSTR const kFastFoldersValueName = TEXT("FolderShortcuts");
32 static LPCTSTR const kCopyHistoryValueName = TEXT("CopyHistory");
33 
34 static NSynchronization::CCriticalSection g_CS;
35 
36 #define Set32(p, v) SetUi32(((Byte *)p), v)
37 #define SetBool(p, v) Set32(p, ((v) ? 1 : 0))
38 
39 #define Get32(p, dest) dest = GetUi32((const Byte *)p);
40 #define Get32_LONG(p, dest) dest = (LONG)GetUi32((const Byte *)p);
41 #define GetBool(p, dest) dest = (GetUi32(p) != 0);
42 
43 /*
44 struct CColumnHeader
45 {
46   UInt32 Version;
47   UInt32 SortID;
48   UInt32 Ascending; // bool
49 };
50 */
51 
52 static const UInt32 kListViewHeaderSize = 3 * 4;
53 static const UInt32 kColumnInfoSize = 3 * 4;
54 static const UInt32 kListViewVersion = 1;
55 
Save(const UString & id) const56 void CListViewInfo::Save(const UString &id) const
57 {
58   const UInt32 dataSize = kListViewHeaderSize + kColumnInfoSize * Columns.Size();
59   CByteArr buf(dataSize);
60 
61   Set32(buf, kListViewVersion)
62   Set32(buf + 4, SortID)
63   SetBool(buf + 8, Ascending)
64   FOR_VECTOR (i, Columns)
65   {
66     const CColumnInfo &column = Columns[i];
67     Byte *p = buf + kListViewHeaderSize + i * kColumnInfoSize;
68     Set32(p, column.PropID)
69     SetBool(p + 4, column.IsVisible)
70     Set32(p + 8, column.Width)
71   }
72   {
73     NSynchronization::CCriticalSectionLock lock(g_CS);
74     CKey key;
75     key.Create(HKEY_CURRENT_USER, kCulumnsKeyName);
76     key.SetValue(GetSystemString(id), (const Byte *)buf, dataSize);
77   }
78 }
79 
Read(const UString & id)80 void CListViewInfo::Read(const UString &id)
81 {
82   Clear();
83   CByteBuffer buf;
84   {
85     NSynchronization::CCriticalSectionLock lock(g_CS);
86     CKey key;
87     if (key.Open(HKEY_CURRENT_USER, kCulumnsKeyName, KEY_READ) != ERROR_SUCCESS)
88       return;
89     if (key.QueryValue_Binary(GetSystemString(id), buf) != ERROR_SUCCESS)
90       return;
91   }
92   unsigned size = (unsigned)buf.Size();
93   if (size < kListViewHeaderSize)
94     return;
95   UInt32 version;
96   Get32(buf, version)
97   if (version != kListViewVersion)
98     return;
99   Get32(buf + 4, SortID)
100   GetBool(buf + 8, Ascending)
101 
102   IsLoaded = true;
103 
104   size -= kListViewHeaderSize;
105   if (size % kColumnInfoSize != 0)
106     return;
107   if (size > 1000 * kColumnInfoSize)
108     return;
109   const unsigned numItems = size / kColumnInfoSize;
110   Columns.ClearAndReserve(numItems);
111   for (unsigned i = 0; i < numItems; i++)
112   {
113     CColumnInfo column;
114     const Byte *p = buf + kListViewHeaderSize + i * kColumnInfoSize;
115     Get32(p, column.PropID)
116     GetBool(p + 4, column.IsVisible)
117     Get32(p + 8, column.Width)
118     Columns.AddInReserved(column);
119   }
120 }
121 
122 
123 /*
124 struct CWindowPosition
125 {
126   RECT Rect;
127   UInt32 Maximized; // bool
128 };
129 
130 struct CPanelsInfo
131 {
132   UInt32 NumPanels;
133   UInt32 CurrentPanel;
134   UInt32 SplitterPos;
135 };
136 */
137 
138 static const UInt32 kWindowPositionHeaderSize = 5 * 4;
139 static const UInt32 kPanelsInfoHeaderSize = 3 * 4;
140 
Save() const141 void CWindowInfo::Save() const
142 {
143   NSynchronization::CCriticalSectionLock lock(g_CS);
144   CKey key;
145   key.Create(HKEY_CURRENT_USER, kCUBasePath);
146   {
147     Byte buf[kWindowPositionHeaderSize];
148     Set32(buf,      (UInt32)rect.left)
149     Set32(buf +  4, (UInt32)rect.top)
150     Set32(buf +  8, (UInt32)rect.right)
151     Set32(buf + 12, (UInt32)rect.bottom)
152     SetBool(buf + 16, maximized)
153     key.SetValue(kPositionValueName, buf, kWindowPositionHeaderSize);
154   }
155   {
156     Byte buf[kPanelsInfoHeaderSize];
157     Set32(buf,      numPanels)
158     Set32(buf +  4, currentPanel)
159     Set32(buf +  8, splitterPos)
160     key.SetValue(kPanelsInfoValueName, buf, kPanelsInfoHeaderSize);
161   }
162 }
163 
QueryBuf(CKey & key,LPCTSTR name,CByteBuffer & buf,UInt32 dataSize)164 static bool QueryBuf(CKey &key, LPCTSTR name, CByteBuffer &buf, UInt32 dataSize)
165 {
166   return key.QueryValue_Binary(name, buf) == ERROR_SUCCESS && buf.Size() == dataSize;
167 }
168 
Read(bool & windowPosDefined,bool & panelInfoDefined)169 void CWindowInfo::Read(bool &windowPosDefined, bool &panelInfoDefined)
170 {
171   windowPosDefined = false;
172   panelInfoDefined = false;
173   NSynchronization::CCriticalSectionLock lock(g_CS);
174   CKey key;
175   if (key.Open(HKEY_CURRENT_USER, kCUBasePath, KEY_READ) != ERROR_SUCCESS)
176     return;
177   CByteBuffer buf;
178   if (QueryBuf(key, kPositionValueName, buf, kWindowPositionHeaderSize))
179   {
180     Get32_LONG(buf,      rect.left)
181     Get32_LONG(buf +  4, rect.top)
182     Get32_LONG(buf +  8, rect.right)
183     Get32_LONG(buf + 12, rect.bottom)
184     GetBool(buf + 16, maximized)
185     windowPosDefined = true;
186   }
187   if (QueryBuf(key, kPanelsInfoValueName, buf, kPanelsInfoHeaderSize))
188   {
189     Get32(buf,      numPanels)
190     Get32(buf +  4, currentPanel)
191     Get32(buf +  8, splitterPos)
192     panelInfoDefined = true;
193   }
194   return;
195 }
196 
197 
SaveUi32Val(const TCHAR * name,UInt32 value)198 static void SaveUi32Val(const TCHAR *name, UInt32 value)
199 {
200   CKey key;
201   key.Create(HKEY_CURRENT_USER, kCUBasePath);
202   key.SetValue(name, value);
203 }
204 
ReadUi32Val(const TCHAR * name,UInt32 & value)205 static bool ReadUi32Val(const TCHAR *name, UInt32 &value)
206 {
207   CKey key;
208   if (key.Open(HKEY_CURRENT_USER, kCUBasePath, KEY_READ) != ERROR_SUCCESS)
209     return false;
210   return key.GetValue_UInt32_IfOk(name, value) == ERROR_SUCCESS;
211 }
212 
SaveToolbarsMask(UInt32 toolbarMask)213 void SaveToolbarsMask(UInt32 toolbarMask)
214 {
215   SaveUi32Val(kToolbars, toolbarMask);
216 }
217 
218 static const UInt32 kDefaultToolbarMask = ((UInt32)1 << 31) | 8 | 4 | 1;
219 
ReadToolbarsMask()220 UInt32 ReadToolbarsMask()
221 {
222   UInt32 mask;
223   if (!ReadUi32Val(kToolbars, mask))
224     return kDefaultToolbarMask;
225   return mask;
226 }
227 
228 
Save() const229 void CListMode::Save() const
230 {
231   UInt32 t = 0;
232   for (int i = 0; i < 2; i++)
233     t |= (Panels[i] & 0xFF) << (i * 8);
234   SaveUi32Val(kListMode, t);
235 }
236 
Read()237 void CListMode::Read()
238 {
239   Init();
240   UInt32 t;
241   if (!ReadUi32Val(kListMode, t))
242     return;
243   for (int i = 0; i < 2; i++)
244   {
245     Panels[i] = t & 0xFF;
246     t >>= 8;
247   }
248 }
249 
GetPanelPathName(UInt32 panelIndex)250 static UString GetPanelPathName(UInt32 panelIndex)
251 {
252   UString s (kPanelPathValueName);
253   s.Add_UInt32(panelIndex);
254   return s;
255 }
256 
SavePanelPath(UInt32 panel,const UString & path)257 void SavePanelPath(UInt32 panel, const UString &path)
258 {
259   NSynchronization::CCriticalSectionLock lock(g_CS);
260   CKey key;
261   key.Create(HKEY_CURRENT_USER, kCUBasePath);
262   key.SetValue(GetPanelPathName(panel), path);
263 }
264 
ReadPanelPath(UInt32 panel,UString & path)265 bool ReadPanelPath(UInt32 panel, UString &path)
266 {
267   NSynchronization::CCriticalSectionLock lock(g_CS);
268   CKey key;
269   if (key.Open(HKEY_CURRENT_USER, kCUBasePath, KEY_READ) != ERROR_SUCCESS)
270     return false;
271   return (key.QueryValue(GetPanelPathName(panel), path) == ERROR_SUCCESS);
272 }
273 
274 
SaveStringList(LPCTSTR valueName,const UStringVector & folders)275 static void SaveStringList(LPCTSTR valueName, const UStringVector &folders)
276 {
277   NSynchronization::CCriticalSectionLock lock(g_CS);
278   CKey key;
279   key.Create(HKEY_CURRENT_USER, kCUBasePath);
280   key.SetValue_Strings(valueName, folders);
281 }
282 
ReadStringList(LPCTSTR valueName,UStringVector & folders)283 static void ReadStringList(LPCTSTR valueName, UStringVector &folders)
284 {
285   folders.Clear();
286   NSynchronization::CCriticalSectionLock lock(g_CS);
287   CKey key;
288   if (key.Open(HKEY_CURRENT_USER, kCUBasePath, KEY_READ) == ERROR_SUCCESS)
289     key.GetValue_Strings(valueName, folders);
290 }
291 
SaveFolderHistory(const UStringVector & folders)292 void SaveFolderHistory(const UStringVector &folders)
293   { SaveStringList(kFolderHistoryValueName, folders); }
ReadFolderHistory(UStringVector & folders)294 void ReadFolderHistory(UStringVector &folders)
295   { ReadStringList(kFolderHistoryValueName, folders); }
296 
SaveFastFolders(const UStringVector & folders)297 void SaveFastFolders(const UStringVector &folders)
298   { SaveStringList(kFastFoldersValueName, folders); }
ReadFastFolders(UStringVector & folders)299 void ReadFastFolders(UStringVector &folders)
300   { ReadStringList(kFastFoldersValueName, folders); }
301 
SaveCopyHistory(const UStringVector & folders)302 void SaveCopyHistory(const UStringVector &folders)
303   { SaveStringList(kCopyHistoryValueName, folders); }
ReadCopyHistory(UStringVector & folders)304 void ReadCopyHistory(UStringVector &folders)
305   { ReadStringList(kCopyHistoryValueName, folders); }
306 
AddUniqueStringToHeadOfList(UStringVector & list,const UString & s)307 void AddUniqueStringToHeadOfList(UStringVector &list, const UString &s)
308 {
309   for (unsigned i = 0; i < list.Size();)
310     if (s.IsEqualTo_NoCase(list[i]))
311       list.Delete(i);
312     else
313       i++;
314   list.Insert(0, s);
315 }
316