ReactOS  0.4.13-dev-99-g7e18b6d
options.c
Go to the documentation of this file.
1 /*
2  * PROJECT: ReactOS Console Configuration DLL
3  * LICENSE: GPL - See COPYING in the top level directory
4  * FILE: dll/cpl/console/options.c
5  * PURPOSE: Options dialog
6  * PROGRAMMERS: Johannes Anderwald (johannes.anderwald@reactos.org)
7  * Hermes Belusca-Maito (hermes.belusca@sfr.fr)
8  */
9 
10 #include "console.h"
11 
12 #define NDEBUG
13 #include <debug.h>
14 
15 #define MAX_VALUE_NAME 16383
16 
17 
18 static INT
20 {
21  return (INT)SendMessageW(ListCtl->hWndList, CB_GETCOUNT, 0, 0);
22 }
23 
24 static ULONG_PTR
26 {
27  return (ULONG_PTR)SendMessageW(ListCtl->hWndList, CB_GETITEMDATA, (WPARAM)Index, 0);
28 }
29 
30 static VOID
32  IN PLIST_CTL ListCtl,
33  IN UINT CodePage)
34 {
35  UINT iItem, iDupItem;
36  CPINFOEXW CPInfo;
37 
38  /*
39  * Add only valid code pages, that is:
40  * - If the CodePage is one of the reserved (alias) values:
41  * CP_ACP == 0 ; CP_OEMCP == 1 ; CP_MACCP == 2 ; CP_THREAD_ACP == 3 ;
42  * or the deprecated CP_SYMBOL == 42 (see http://archives.miloush.net/michkap/archive/2005/11/08/490495.html)
43  * it is considered invalid.
44  * - If IsValidCodePage() fails because the code page is listed but
45  * not installed on the system, it is also considered invalid.
46  */
47  if (CodePage == CP_ACP || CodePage == CP_OEMCP || CodePage == CP_MACCP ||
48  CodePage == CP_THREAD_ACP || CodePage == CP_SYMBOL || !IsValidCodePage(CodePage))
49  {
50  return;
51  }
52 
53  /* Retrieve the code page display name */
54  if (!GetCPInfoExW(CodePage, 0, &CPInfo))
55  {
56  /* We failed, just use the code page value as its name */
57  // _ultow(CodePage, CPInfo.CodePageName, 10);
58  StringCchPrintfW(CPInfo.CodePageName, ARRAYSIZE(CPInfo.CodePageName), L"%lu", CodePage);
59  }
60 
61  /* Add the code page into the list, sorted by code page value. Avoid any duplicates. */
62  iDupItem = CB_ERR;
63  iItem = BisectListSortedByValue(ListCtl, CodePage, &iDupItem, TRUE);
64  if (iItem == CB_ERR)
65  iItem = 0;
66  if (iDupItem != CB_ERR)
67  return;
68  iItem = (UINT)SendMessageW(ListCtl->hWndList, CB_INSERTSTRING, iItem, (LPARAM)CPInfo.CodePageName);
69  if (iItem != CB_ERR && iItem != CB_ERRSPACE)
70  iItem = SendMessageW(ListCtl->hWndList, CB_SETITEMDATA, iItem, CodePage);
71 }
72 
73 static VOID
75  IN HWND hDlg)
76 {
77  LIST_CTL ListCtl;
78  HKEY hKey;
79  DWORD dwIndex, dwSize, dwType;
80  UINT CodePage;
81  WCHAR szValueName[MAX_VALUE_NAME];
82 
83  // #define REGSTR_PATH_CODEPAGE TEXT("System\\CurrentControlSet\\Control\\Nls\\CodePage")
84  /* Open the Nls\CodePage key */
86  L"System\\CurrentControlSet\\Control\\Nls\\CodePage",
87  0,
89  &hKey) != ERROR_SUCCESS)
90  {
91  return;
92  }
93 
94  ListCtl.hWndList = GetDlgItem(hDlg, IDL_CODEPAGE);
95  ListCtl.GetCount = List_GetCount;
96  ListCtl.GetData = List_GetData;
97 
98  /* Enumerate all the available code pages on the system */
99  dwSize = ARRAYSIZE(szValueName);
100  dwIndex = 0;
101  while (RegEnumValueW(hKey, dwIndex, szValueName, &dwSize,
102  NULL, &dwType, NULL, NULL) == ERROR_SUCCESS) // != ERROR_NO_MORE_ITEMS
103  {
104  /* Ignore these parameters, prepare for next iteration */
105  dwSize = ARRAYSIZE(szValueName);
106  ++dwIndex;
107 
108  /* Check the value type validity */
109  if (dwType != REG_SZ)
110  continue;
111 
112  /*
113  * Add the code page into the list.
114  * If _wtol fails and returns 0, the code page is considered invalid
115  * (and indeed this value corresponds to the CP_ACP alias too).
116  */
117  CodePage = (UINT)_wtol(szValueName);
118  if (CodePage == 0) continue;
119  AddCodePage(&ListCtl, CodePage);
120  }
121 
122  RegCloseKey(hKey);
123 
124  /* Add the special UTF-7 (CP_UTF7 65000) and UTF-8 (CP_UTF8 65001) code pages */
125  AddCodePage(&ListCtl, CP_UTF7);
126  AddCodePage(&ListCtl, CP_UTF8);
127 
128  /* Find and select the current code page in the sorted list */
129  if (BisectListSortedByValue(&ListCtl, ConInfo->CodePage, &CodePage, FALSE) == CB_ERR ||
130  CodePage == CB_ERR)
131  {
132  /* Not found, select the first element */
133  CodePage = 0;
134  }
135  SendMessageW(ListCtl.hWndList, CB_SETCURSEL, (WPARAM)CodePage, 0);
136 }
137 
138 static VOID
140  IN HWND hDlg,
141  IN PCONSOLE_STATE_INFO pConInfo)
142 {
143  /* Update the cursor size */
144  if (pConInfo->CursorSize <= 25)
145  {
146  /* Small cursor */
148  // CheckDlgButton(hDlg, IDC_RADIO_SMALL_CURSOR , BST_CHECKED);
149  // CheckDlgButton(hDlg, IDC_RADIO_MEDIUM_CURSOR, BST_UNCHECKED);
150  // CheckDlgButton(hDlg, IDC_RADIO_LARGE_CURSOR , BST_UNCHECKED);
151  }
152  else if (pConInfo->CursorSize <= 50)
153  {
154  /* Medium cursor */
156  // CheckDlgButton(hDlg, IDC_RADIO_SMALL_CURSOR , BST_UNCHECKED);
157  // CheckDlgButton(hDlg, IDC_RADIO_MEDIUM_CURSOR, BST_CHECKED);
158  // CheckDlgButton(hDlg, IDC_RADIO_LARGE_CURSOR , BST_UNCHECKED);
159  }
160  else /* if (pConInfo->CursorSize <= 100) */
161  {
162  /* Large cursor */
164  // CheckDlgButton(hDlg, IDC_RADIO_SMALL_CURSOR , BST_UNCHECKED);
165  // CheckDlgButton(hDlg, IDC_RADIO_MEDIUM_CURSOR, BST_UNCHECKED);
166  // CheckDlgButton(hDlg, IDC_RADIO_LARGE_CURSOR , BST_CHECKED);
167  }
168 
169  /* Update the number of history buffers */
171  SetDlgItemInt(hDlg, IDC_EDIT_NUM_BUFFER, pConInfo->NumberOfHistoryBuffers, FALSE);
172 
173  /* Update the history buffer size */
175  SetDlgItemInt(hDlg, IDC_EDIT_BUFFER_SIZE, pConInfo->HistoryBufferSize, FALSE);
176 
177  /* Update discard duplicates */
179  pConInfo->HistoryNoDup ? BST_CHECKED : BST_UNCHECKED);
180 
181  /* Update full/window screen state */
182  if (pConInfo->FullScreen)
183  {
185  // CheckDlgButton(hDlg, IDC_RADIO_DISPLAY_WINDOW, BST_UNCHECKED);
186  // CheckDlgButton(hDlg, IDC_RADIO_DISPLAY_FULL , BST_CHECKED);
187  }
188  else
189  {
191  // CheckDlgButton(hDlg, IDC_RADIO_DISPLAY_WINDOW, BST_CHECKED);
192  // CheckDlgButton(hDlg, IDC_RADIO_DISPLAY_FULL , BST_UNCHECKED);
193  }
194 
195  /* Update "Quick-edit" state */
197  pConInfo->QuickEdit ? BST_CHECKED : BST_UNCHECKED);
198 
199  /* Update "Insert mode" state */
201  pConInfo->InsertMode ? BST_CHECKED : BST_UNCHECKED);
202 }
203 
204 INT_PTR
205 CALLBACK
207  UINT uMsg,
208  WPARAM wParam,
209  LPARAM lParam)
210 {
211  switch (uMsg)
212  {
213  case WM_INITDIALOG:
214  {
215  BuildCodePageList(hDlg);
217  return TRUE;
218  }
219 
220  case WM_NOTIFY:
221  {
222  LPPSHNOTIFY lppsn = (LPPSHNOTIFY)lParam;
223 
224  if (lppsn->hdr.code == UDN_DELTAPOS)
225  {
226  LPNMUPDOWN lpnmud = (LPNMUPDOWN)lParam;
227 
228  if (lppsn->hdr.idFrom == IDC_UPDOWN_BUFFER_SIZE)
229  {
230  lpnmud->iPos = min(max(lpnmud->iPos + lpnmud->iDelta, 1), 999);
231  ConInfo->HistoryBufferSize = lpnmud->iPos;
232  PropSheet_Changed(GetParent(hDlg), hDlg);
233  }
234  else if (lppsn->hdr.idFrom == IDC_UPDOWN_NUM_BUFFER)
235  {
236  lpnmud->iPos = min(max(lpnmud->iPos + lpnmud->iDelta, 1), 999);
238  PropSheet_Changed(GetParent(hDlg), hDlg);
239  }
240  }
241  else if (lppsn->hdr.code == PSN_APPLY)
242  {
243  ApplyConsoleInfo(hDlg);
244  return TRUE;
245  }
246  break;
247  }
248 
249  case WM_COMMAND:
250  {
251  if (HIWORD(wParam) == BN_CLICKED)
252  {
253  switch (LOWORD(wParam))
254  {
256  {
257  ConInfo->CursorSize = 25;
258  PropSheet_Changed(GetParent(hDlg), hDlg);
259  break;
260  }
262  {
263  ConInfo->CursorSize = 50;
264  PropSheet_Changed(GetParent(hDlg), hDlg);
265  break;
266  }
268  {
269  ConInfo->CursorSize = 100;
270  PropSheet_Changed(GetParent(hDlg), hDlg);
271  break;
272  }
274  {
276  PropSheet_Changed(GetParent(hDlg), hDlg);
277  break;
278  }
280  {
282  PropSheet_Changed(GetParent(hDlg), hDlg);
283  break;
284  }
286  {
287  ConInfo->QuickEdit = (IsDlgButtonChecked(hDlg, IDC_CHECK_QUICK_EDIT) == BST_CHECKED); // BST_UNCHECKED or BST_INDETERMINATE => FALSE
288  PropSheet_Changed(GetParent(hDlg), hDlg);
289  break;
290  }
292  {
293  ConInfo->InsertMode = (IsDlgButtonChecked(hDlg, IDC_CHECK_INSERT_MODE) == BST_CHECKED); // BST_UNCHECKED or BST_INDETERMINATE => FALSE
294  PropSheet_Changed(GetParent(hDlg), hDlg);
295  break;
296  }
298  {
299  ConInfo->HistoryNoDup = (IsDlgButtonChecked(hDlg, IDC_CHECK_DISCARD_DUPLICATES) == BST_CHECKED); // BST_UNCHECKED or BST_INDETERMINATE => FALSE
300  PropSheet_Changed(GetParent(hDlg), hDlg);
301  break;
302  }
303  }
304  }
305  else
306  if (HIWORD(wParam) == EN_KILLFOCUS)
307  {
308  switch (LOWORD(wParam))
309  {
311  {
312  DWORD sizeBuff;
313 
314  sizeBuff = GetDlgItemInt(hDlg, IDC_EDIT_BUFFER_SIZE, NULL, FALSE);
315  sizeBuff = min(max(sizeBuff, 1), 999);
316 
317  ConInfo->HistoryBufferSize = sizeBuff;
318  PropSheet_Changed(GetParent(hDlg), hDlg);
319  break;
320  }
321  case IDC_EDIT_NUM_BUFFER:
322  {
323  DWORD numBuff;
324 
325  numBuff = GetDlgItemInt(hDlg, IDC_EDIT_NUM_BUFFER, NULL, FALSE);
326  numBuff = min(max(numBuff, 1), 999);
327 
328  ConInfo->NumberOfHistoryBuffers = numBuff;
329  PropSheet_Changed(GetParent(hDlg), hDlg);
330  break;
331  }
332  }
333  }
334  else
336  (LOWORD(wParam) == IDL_CODEPAGE))
337  {
339  INT iItem;
340  UINT CodePage;
341 
342  iItem = (INT)SendMessageW(hWndList, CB_GETCURSEL, 0, 0);
343  if (iItem == CB_ERR)
344  break;
345 
346  CodePage = (UINT)SendMessageW(hWndList, CB_GETITEMDATA, iItem, 0);
347  if (CodePage == CB_ERR)
348  break;
349 
350  ConInfo->CodePage = CodePage;
351 
352  /* Change the property sheet state only if the user validated */
353  if (HIWORD(wParam) == CBN_SELENDOK)
354  PropSheet_Changed(GetParent(hDlg), hDlg);
355  }
356 
357  break;
358  }
359 
360  default:
361  break;
362  }
363 
364  return FALSE;
365 }
#define CB_SETITEMDATA
Definition: winuser.h:1927
BOOL WINAPI CheckDlgButton(_In_ HWND, _In_ int, _In_ UINT)
#define IN
Definition: typedefs.h:38
#define max(a, b)
Definition: svc.c:63
#define IDC_CHECK_INSERT_MODE
Definition: resource.h:20
#define TRUE
Definition: types.h:120
#define ERROR_SUCCESS
Definition: deptool.c:10
#define IDC_RADIO_LARGE_CURSOR
Definition: resource.h:28
#define IDC_RADIO_SMALL_CURSOR
Definition: resource.h:26
struct _PSHNOTIFY * LPPSHNOTIFY
#define CP_UTF7
Definition: winnls.h:232
WCHAR CodePageName[MAX_PATH]
Definition: winnls.h:596
#define CP_ACP
Definition: compat.h:99
#define CB_GETITEMDATA
Definition: winuser.h:1911
struct _NM_UPDOWN * LPNMUPDOWN
#define INT
Definition: polytest.cpp:20
#define CALLBACK
Definition: compat.h:27
#define ARRAYSIZE(array)
Definition: filtermapper.c:47
UINT_PTR WPARAM
Definition: windef.h:207
#define PSN_APPLY
Definition: prsht.h:117
#define IDC_CHECK_DISCARD_DUPLICATES
Definition: resource.h:21
int32_t INT_PTR
Definition: typedefs.h:62
static HWND hWndList[5+1]
Definition: SetParent.c:10
#define CP_SYMBOL
Definition: winnls.h:231
int32_t INT
Definition: typedefs.h:56
#define CB_GETCURSEL
Definition: winuser.h:1904
WPARAM wParam
Definition: combotst.c:138
#define IDC_EDIT_BUFFER_SIZE
Definition: resource.h:22
HWND hWndList
Definition: console.h:69
uint32_t ULONG_PTR
Definition: typedefs.h:63
UINT code
Definition: winuser.h:3112
NMHDR hdr
Definition: prsht.h:312
#define EN_KILLFOCUS
Definition: winuser.h:1986
LONG WINAPI RegCloseKey(HKEY hKey)
Definition: reg.c:423
#define IDC_CHECK_QUICK_EDIT
Definition: resource.h:19
#define CP_UTF8
Definition: nls.h:20
#define CBN_SELENDOK
Definition: winuser.h:1942
UINT_PTR idFrom
Definition: winuser.h:3111
#define IDC_RADIO_DISPLAY_FULL
Definition: resource.h:30
#define MAKELONG(a, b)
Definition: typedefs.h:248
#define CB_INSERTSTRING
Definition: winuser.h:1918
LONG WINAPI RegEnumValueW(_In_ HKEY hKey, _In_ DWORD index, _Out_ LPWSTR value, _Inout_ PDWORD val_count, _Reserved_ PDWORD reserved, _Out_opt_ PDWORD type, _Out_opt_ LPBYTE data, _Inout_opt_ PDWORD count)
Definition: reg.c:2867
smooth NULL
Definition: ftsmooth.c:416
UINT WINAPI GetDlgItemInt(_In_ HWND, _In_ int, _Out_opt_ PBOOL, _In_ BOOL)
static INT List_GetCount(IN PLIST_CTL ListCtl)
Definition: options.c:19
VOID ApplyConsoleInfo(HWND hwndDlg)
Definition: console.c:88
LONG_PTR LPARAM
Definition: windef.h:208
#define UDM_SETRANGE
Definition: commctrl.h:2113
UINT WINAPI IsDlgButtonChecked(_In_ HWND, _In_ int)
#define CB_ERR
Definition: winuser.h:2389
static VOID BuildCodePageList(IN HWND hDlg)
Definition: options.c:74
HWND WINAPI GetDlgItem(_In_opt_ HWND, _In_ int)
__wchar_t WCHAR
Definition: xmlstorage.h:180
#define PropSheet_Changed(d, w)
Definition: prsht.h:326
ULONG HistoryBufferSize
Definition: settings.h:50
static const UCHAR Index[8]
Definition: usbohci.c:18
#define BN_CLICKED
Definition: winuser.h:1886
unsigned long DWORD
Definition: ntddk_ex.h:95
LRESULT WINAPI SendDlgItemMessageW(_In_ HWND, _In_ int, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
PLIST_GETDATA GetData
Definition: console.h:71
static ULONG_PTR List_GetData(IN PLIST_CTL ListCtl, IN INT Index)
Definition: options.c:25
PLIST_GETCOUNT GetCount
Definition: console.h:70
BOOL WINAPI SetDlgItemInt(_In_ HWND, _In_ int, _In_ UINT, _In_ BOOL)
#define UDN_DELTAPOS
Definition: commctrl.h:2141
static const WCHAR L[]
Definition: oid.c:1250
#define CB_ERRSPACE
Definition: winuser.h:2390
#define CB_SETCURSEL
Definition: winuser.h:1922
#define WM_COMMAND
Definition: winuser.h:1716
#define MAX_VALUE_NAME
Definition: options.c:15
#define BST_UNCHECKED
Definition: winuser.h:199
#define IDL_CODEPAGE
Definition: resource.h:31
int iDelta
Definition: commctrl.h:2138
HWND WINAPI GetParent(_In_ HWND)
BOOL WINAPI IsValidCodePage(UINT CodePage)
Definition: nls.c:1468
ULONG NumberOfHistoryBuffers
Definition: settings.h:51
#define KEY_QUERY_VALUE
Definition: nt_native.h:1016
static VOID UpdateDialogElements(IN HWND hDlg, IN PCONSOLE_STATE_INFO pConInfo)
Definition: options.c:139
LRESULT WINAPI SendMessageW(_In_ HWND, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
STRSAFEAPI StringCchPrintfW(STRSAFE_LPWSTR pszDest, size_t cchDest, STRSAFE_LPCWSTR pszFormat,...)
Definition: strsafe.h:530
PCONSOLE_STATE_INFO ConInfo
Definition: console.c:23
#define min(a, b)
Definition: monoChain.cc:55
unsigned int UINT
Definition: ndis.h:50
_Check_return_ _CRTIMP long __cdecl _wtol(_In_z_ const wchar_t *_Str)
#define IDC_RADIO_MEDIUM_CURSOR
Definition: resource.h:27
#define CBN_SELCHANGE
Definition: winuser.h:1940
#define BST_CHECKED
Definition: winuser.h:197
static VOID AddCodePage(IN PLIST_CTL ListCtl, IN UINT CodePage)
Definition: options.c:31
#define IDC_EDIT_NUM_BUFFER
Definition: resource.h:24
#define IDC_UPDOWN_BUFFER_SIZE
Definition: resource.h:23
#define IDC_RADIO_DISPLAY_WINDOW
Definition: resource.h:29
#define HIWORD(l)
Definition: typedefs.h:246
LONG WINAPI RegOpenKeyExW(HKEY hKey, LPCWSTR lpSubKey, DWORD ulOptions, REGSAM samDesired, PHKEY phkResult)
Definition: reg.c:3381
BOOL WINAPI GetCPInfoExW(UINT CodePage, DWORD dwFlags, LPCPINFOEXW lpCPInfoEx)
Definition: nls.c:1958
INT_PTR CALLBACK OptionsProc(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
Definition: options.c:206
#define IDC_UPDOWN_NUM_BUFFER
Definition: resource.h:25
BOOL WINAPI CheckRadioButton(_In_ HWND, _In_ int, _In_ int, _In_ int)
#define CB_GETCOUNT
Definition: winuser.h:1903
UINT BisectListSortedByValue(IN PLIST_CTL ListCtl, IN ULONG_PTR Value, OUT PUINT pValueItem OPTIONAL, IN BOOL BisectRightOrLeft)
Definition: utils.c:115
#define CP_THREAD_ACP
Definition: winnls.h:230
#define WM_INITDIALOG
Definition: winuser.h:1715
LPARAM lParam
Definition: combotst.c:139
#define LOWORD(l)
Definition: pedump.c:82
#define CP_OEMCP
Definition: winnls.h:228
PSDBQUERYRESULT_VISTA PVOID DWORD * dwSize
Definition: env.c:54
#define WM_NOTIFY
Definition: richedit.h:61
#define CP_MACCP
Definition: winnls.h:229
#define HKEY_LOCAL_MACHINE
Definition: winreg.h:12
#define KEY_ENUMERATE_SUB_KEYS
Definition: nt_native.h:1019
#define REG_SZ
Definition: layer.c:22