Added regedit unit test, a couple minor changes to regedit.
[wine] / dlls / comctl32 / hotkey.c
1 /*
2  * Hotkey control
3  *
4  * Copyright 1998, 1999 Eric Kohl
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
19  *
20  * NOTES
21  *   Development in progress. An author is needed! Any volunteers?
22  *   I will only improve this control once in a while.
23  *     Eric <ekohl@abo.rhein-zeitung.de>
24  *
25  * TODO:
26  *   - Some messages.
27  *   - Display code.
28  */
29
30 #include <string.h>
31 #include "winbase.h"
32 #include "commctrl.h"
33 #include "wine/debug.h"
34
35 WINE_DEFAULT_DEBUG_CHANNEL(hotkey);
36
37 typedef struct tagHOTKEY_INFO
38 {
39     HFONT hFont;
40     BOOL  bFocus;
41     INT   nHeight;
42 } HOTKEY_INFO;
43
44 #define HOTKEY_GetInfoPtr(hwnd) ((HOTKEY_INFO *)GetWindowLongA (hwnd, 0))
45
46
47 /* << HOTHEY_GetHotKey >> */
48 /* << HOTHEY_SetHotKey >> */
49 /* << HOTHEY_SetRules >> */
50
51
52
53 /* << HOTKEY_Char >> */
54
55
56 static LRESULT
57 HOTKEY_Create (HWND hwnd, WPARAM wParam, LPARAM lParam)
58 {
59     HOTKEY_INFO *infoPtr;
60     TEXTMETRICA tm;
61     HDC hdc;
62
63     /* allocate memory for info structure */
64     infoPtr = (HOTKEY_INFO *)COMCTL32_Alloc (sizeof(HOTKEY_INFO));
65     SetWindowLongA (hwnd, 0, (DWORD)infoPtr);
66
67     /* initialize info structure */
68
69
70     /* get default font height */
71     hdc = GetDC (hwnd);
72     GetTextMetricsA (hdc, &tm);
73     infoPtr->nHeight = tm.tmHeight;
74     ReleaseDC (hwnd, hdc);
75
76     return 0;
77 }
78
79
80 static LRESULT
81 HOTKEY_Destroy (HWND hwnd, WPARAM wParam, LPARAM lParam)
82 {
83     HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd);
84
85
86
87     /* free hotkey info data */
88     COMCTL32_Free (infoPtr);
89     SetWindowLongA (hwnd, 0, 0);
90     return 0;
91 }
92
93
94 static LRESULT
95 HOTKEY_EraseBackground (HWND hwnd, WPARAM wParam, LPARAM lParam)
96 {
97     /* HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
98     HBRUSH hBrush;
99     RECT   rc;
100
101     hBrush =
102         (HBRUSH)SendMessageA (GetParent (hwnd), WM_CTLCOLOREDIT,
103                                 wParam, (LPARAM)hwnd);
104     if (hBrush)
105         hBrush = (HBRUSH)GetStockObject (WHITE_BRUSH);
106     GetClientRect (hwnd, &rc);
107
108     FillRect ((HDC)wParam, &rc, hBrush);
109
110     return -1;
111 }
112
113
114 inline static LRESULT
115 HOTKEY_GetFont (HWND hwnd, WPARAM wParam, LPARAM lParam)
116 {
117     HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd);
118
119     return infoPtr->hFont;
120 }
121
122
123 static LRESULT
124 HOTKEY_KeyDown (HWND hwnd, WPARAM wParam, LPARAM lParam)
125 {
126     /* HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
127
128     switch (wParam) {
129         case VK_RETURN:
130         case VK_TAB:
131         case VK_SPACE:
132         case VK_DELETE:
133         case VK_ESCAPE:
134         case VK_BACK:
135             return DefWindowProcA (hwnd, WM_KEYDOWN, wParam, lParam);
136
137         case VK_SHIFT:
138         case VK_CONTROL:
139         case VK_MENU:
140             FIXME("modifier key pressed!\n");
141             break;
142
143         default:
144             FIXME(" %d\n", wParam);
145             break;
146     }
147
148     return TRUE;
149 }
150
151
152 static LRESULT
153 HOTKEY_KeyUp (HWND hwnd, WPARAM wParam, LPARAM lParam)
154 {
155     /* HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
156
157     FIXME(" %d\n", wParam);
158
159     return 0;
160 }
161
162
163 static LRESULT
164 HOTKEY_KillFocus (HWND hwnd, WPARAM wParam, LPARAM lParam)
165 {
166     HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd);
167
168     infoPtr->bFocus = FALSE;
169     DestroyCaret ();
170
171     return 0;
172 }
173
174
175 static LRESULT
176 HOTKEY_LButtonDown (HWND hwnd, WPARAM wParam, LPARAM lParam)
177 {
178 /*    HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
179
180     SetFocus (hwnd);
181
182     return 0;
183 }
184
185
186 inline static LRESULT
187 HOTKEY_NCCreate (HWND hwnd, WPARAM wParam, LPARAM lParam)
188 {
189     DWORD dwExStyle = GetWindowLongA (hwnd, GWL_EXSTYLE);
190     SetWindowLongA (hwnd, GWL_EXSTYLE, dwExStyle | WS_EX_CLIENTEDGE);
191     return DefWindowProcA (hwnd, WM_NCCREATE, wParam, lParam);
192 }
193
194
195
196
197
198 static LRESULT
199 HOTKEY_SetFocus (HWND hwnd, WPARAM wParam, LPARAM lParam)
200 {
201     HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd);
202
203     infoPtr->bFocus = TRUE;
204
205
206     CreateCaret (hwnd, (HBITMAP)0, 1, infoPtr->nHeight);
207
208     SetCaretPos (1, 1);
209
210     ShowCaret (hwnd);
211
212
213     return 0;
214 }
215
216
217 inline static LRESULT
218 HOTKEY_SetFont (HWND hwnd, WPARAM wParam, LPARAM lParam)
219 {
220     HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd);
221     TEXTMETRICA tm;
222     HDC hdc;
223     HFONT hOldFont = 0;
224
225     infoPtr->hFont = (HFONT)wParam;
226
227     hdc = GetDC (hwnd);
228     if (infoPtr->hFont)
229         hOldFont = SelectObject (hdc, infoPtr->hFont);
230
231     GetTextMetricsA (hdc, &tm);
232     infoPtr->nHeight = tm.tmHeight;
233
234     if (infoPtr->hFont)
235         SelectObject (hdc, hOldFont);
236     ReleaseDC (hwnd, hdc);
237
238     if (LOWORD(lParam)) {
239
240         FIXME("force redraw!\n");
241
242     }
243
244     return 0;
245 }
246
247
248 static LRESULT WINE_UNUSED
249 HOTKEY_SysKeyDown (HWND hwnd, WPARAM wParam, LPARAM lParam)
250 {
251     /* HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
252
253     switch (wParam) {
254         case VK_RETURN:
255         case VK_TAB:
256         case VK_SPACE:
257         case VK_DELETE:
258         case VK_ESCAPE:
259         case VK_BACK:
260             return DefWindowProcA (hwnd, WM_SYSKEYDOWN, wParam, lParam);
261
262         case VK_SHIFT:
263         case VK_CONTROL:
264         case VK_MENU:
265             FIXME("modifier key pressed!\n");
266             break;
267
268         default:
269             FIXME(" %d\n", wParam);
270             break;
271     }
272
273     return TRUE;
274 }
275
276
277 static LRESULT WINE_UNUSED
278 HOTKEY_SysKeyUp (HWND hwnd, WPARAM wParam, LPARAM lParam)
279 {
280     /* HOTKEY_INFO *infoPtr = HOTKEY_GetInfoPtr (hwnd); */
281
282     FIXME(" %d\n", wParam);
283
284     return 0;
285 }
286
287
288
289 static LRESULT WINAPI
290 HOTKEY_WindowProc (HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
291 {
292     TRACE("hwnd=%x msg=%x wparam=%x lparam=%lx\n", hwnd, uMsg, wParam, lParam);
293     if (!HOTKEY_GetInfoPtr (hwnd) && (uMsg != WM_CREATE))
294         return DefWindowProcA (hwnd, uMsg, wParam, lParam);
295     switch (uMsg)
296     {
297 /*      case HKM_GETHOTKEY: */
298 /*      case HKM_SETHOTKEY: */
299 /*      case HKM_SETRULES: */
300
301 /*      case WM_CHAR: */
302
303         case WM_CREATE:
304             return HOTKEY_Create (hwnd, wParam, lParam);
305
306         case WM_DESTROY:
307             return HOTKEY_Destroy (hwnd, wParam, lParam);
308
309         case WM_ERASEBKGND:
310             return HOTKEY_EraseBackground (hwnd, wParam, lParam);
311
312         case WM_GETDLGCODE:
313             return DLGC_WANTCHARS | DLGC_WANTARROWS;
314
315         case WM_GETFONT:
316             return HOTKEY_GetFont (hwnd, wParam, lParam);
317
318         case WM_KEYDOWN:
319         case WM_SYSKEYDOWN:
320             return HOTKEY_KeyDown (hwnd, wParam, lParam);
321
322         case WM_KEYUP:
323         case WM_SYSKEYUP:
324             return HOTKEY_KeyUp (hwnd, wParam, lParam);
325
326         case WM_KILLFOCUS:
327             return HOTKEY_KillFocus (hwnd, wParam, lParam);
328
329         case WM_LBUTTONDOWN:
330             return HOTKEY_LButtonDown (hwnd, wParam, lParam);
331
332         case WM_NCCREATE:
333             return HOTKEY_NCCreate (hwnd, wParam, lParam);
334
335 /*      case WM_PAINT: */
336
337         case WM_SETFOCUS:
338             return HOTKEY_SetFocus (hwnd, wParam, lParam);
339
340         case WM_SETFONT:
341             return HOTKEY_SetFont (hwnd, wParam, lParam);
342
343 /*      case WM_SYSCHAR: */
344
345         default:
346             if (uMsg >= WM_USER)
347                 ERR("unknown msg %04x wp=%08x lp=%08lx\n",
348                      uMsg, wParam, lParam);
349             return DefWindowProcA (hwnd, uMsg, wParam, lParam);
350     }
351     return 0;
352 }
353
354
355 VOID
356 HOTKEY_Register (void)
357 {
358     WNDCLASSA wndClass;
359
360     ZeroMemory (&wndClass, sizeof(WNDCLASSA));
361     wndClass.style         = CS_GLOBALCLASS;
362     wndClass.lpfnWndProc   = (WNDPROC)HOTKEY_WindowProc;
363     wndClass.cbClsExtra    = 0;
364     wndClass.cbWndExtra    = sizeof(HOTKEY_INFO *);
365     wndClass.hCursor       = 0;
366     wndClass.hbrBackground = 0;
367     wndClass.lpszClassName = HOTKEY_CLASSA;
368
369     RegisterClassA (&wndClass);
370 }
371
372
373 VOID
374 HOTKEY_Unregister (void)
375 {
376     UnregisterClassA (HOTKEY_CLASSA, (HINSTANCE)NULL);
377 }
378