source: trunk/src/user32/wndclass.cpp@ 215

Last change on this file since 215 was 215, checked in by sandervl, 26 years ago

Spy and window message changes

File size: 33.9 KB
Line 
1/* $Id: wndclass.cpp,v 1.9 1999-06-26 13:21:11 sandervl Exp $ */
2
3/*
4 * Win32 Window Class Managment Code for OS/2
5 *
6 * 18-07-1998 SvL: Merged all class code into this file + bug fixes
7 * Register all system classes at dll init
8 * Rewrote incorrect callback code
9 *
10 * Copyright 1998 Sander van Leeuwen (sandervl@xs4all.nl)
11 *
12 *
13 * Project Odin Software License can be found in LICENSE.TXT
14 *
15 */
16#include <os2win.h>
17#include <stdarg.h>
18#include <stdio.h>
19#include <string.h>
20#include <stdlib.h>
21#include <assert.h>
22#include <misc.h>
23#include <wndproc.h>
24#include <wndclass.h>
25#include <nameid.h>
26#include <spy.h>
27#include "hooks.h"
28
29//default window handlers that are registered by RegisterClass are called
30//in this callback handler
31LRESULT EXPENTRY_O32 OS2ToWinCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam);
32//default window handlers that are queried by GetClassInfo/GetClassLong is really
33//this callback handler
34LRESULT WIN32API WinToOS2Callback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam);
35
36#ifdef DEBUG
37char *GetMsgText(int Msg);
38#endif
39
40DWORD MapOEMToRealKey(DWORD wParam, DWORD lParam);
41
42WNDPROC_O32 ButtonHandler = 0;
43WNDPROC_O32 ListboxHandler = 0;
44WNDPROC_O32 ComboboxHandler = 0;
45WNDPROC_O32 EditHandler = 0;
46WNDPROC_O32 MdiClientHandler = 0;
47WNDPROC_O32 ScrollbarHandler = 0;
48WNDPROC_O32 StaticHandler = 0;
49
50HWND hwndButton = 0;
51HWND hwndListbox = 0;
52HWND hwndEdit = 0;
53HWND hwndCombobox = 0;
54HWND hwndScrollbar = 0;
55HWND hwndMdiClient = 0;
56HWND hwndStatic = 0;
57
58Win32WindowClass *ButtonClass = 0;
59Win32WindowClass *ListboxClass = 0;
60Win32WindowClass *EditClass = 0;
61Win32WindowClass *ComboboxClass = 0;
62Win32WindowClass *MdiClientClass = 0;
63Win32WindowClass *ScrollbarClass = 0;
64Win32WindowClass *StaticClass = 0;
65//******************************************************************************
66//******************************************************************************
67LRESULT WIN32API ButtonCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
68{
69 DWORD dwStyle, dwExStyle;
70
71 PostSpyMessage(hwnd, Msg, wParam, lParam);
72 switch(Msg)
73 {
74 case WM_MOUSEACTIVATE:
75 //Open32 sends an OS/2 window message for a button click
76 if(HIWORD(lParam) == 0x71) //WM_BUTTONCLICKFIRST
77 {
78 lParam = (WM_LBUTTONDOWN << 16) | LOWORD(lParam);
79 }
80 dwStyle = GetWindowLongA(hwnd, GWL_STYLE);
81 dwExStyle = GetWindowLongA(hwnd, GWL_EXSTYLE);
82
83 if(dwStyle & WS_CHILD && !(dwExStyle & WS_EX_NOPARENTNOTIFY) )
84 {
85 HWND hwndParent = GetParent(hwnd);
86
87 Win32WindowProc *parentwnd = Win32WindowProc::FindProc(hwndParent);
88 if(parentwnd) {
89 LRESULT rc = parentwnd->SendMessageA(hwndParent, Msg, wParam, lParam);
90 if(rc) return TRUE;
91 }
92 }
93 break;
94 case WM_CREATE:
95 case WM_DESTROY:
96 case WM_LBUTTONDOWN:
97 case WM_MBUTTONDOWN:
98 case WM_RBUTTONDOWN:
99 NotifyParent(hwnd, Msg, wParam, lParam);
100 break;
101 }
102 return ButtonHandler(hwnd, Msg, wParam, lParam);
103}
104//******************************************************************************
105//******************************************************************************
106LRESULT WIN32API ListboxCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
107{
108 PostSpyMessage(hwnd, Msg, wParam, lParam);
109 return ListboxHandler(hwnd, Msg, wParam, lParam);
110}
111//******************************************************************************
112//******************************************************************************
113LRESULT WIN32API ComboboxCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
114{
115 PostSpyMessage(hwnd, Msg, wParam, lParam);
116 return ComboboxHandler(hwnd, Msg, wParam, lParam);
117}
118//******************************************************************************
119//******************************************************************************
120LRESULT WIN32API MdiClientCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
121{
122 PostSpyMessage(hwnd, Msg, wParam, lParam);
123 return MdiClientHandler(hwnd, Msg, wParam, lParam);
124}
125//******************************************************************************
126//******************************************************************************
127LRESULT WIN32API EditCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
128{
129 PostSpyMessage(hwnd, Msg, wParam, lParam);
130 return EditHandler(hwnd, Msg, wParam, lParam);
131}
132//******************************************************************************
133//******************************************************************************
134LRESULT WIN32API ScrollbarCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
135{
136 PostSpyMessage(hwnd, Msg, wParam, lParam);
137 return ScrollbarHandler(hwnd, Msg, wParam, lParam);
138}
139//******************************************************************************
140//******************************************************************************
141LRESULT WIN32API StaticCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
142{
143 PostSpyMessage(hwnd, Msg, wParam, lParam);
144 return StaticHandler(hwnd, Msg, wParam, lParam);
145}
146//******************************************************************************
147//SvL: 18-7-'98, Registers system window classes (button, listbox etc etc)
148//******************************************************************************
149void RegisterSystemClasses(ULONG hModule)
150{
151 WNDCLASSA wndclass;
152 HWND hwnd;
153
154 if(O32_GetClassInfo(NULL, "BUTTON", &wndclass)) {
155 dprintf(("Create BUTTON System class"));
156 ButtonClass = new Win32WindowClass(ButtonCallback, "BUTTON", hModule);
157 ButtonHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
158 hwndButton = O32_CreateWindow("BUTTON", "BUTTON", 0, 0, 0, 0, 0, 0, 0, 0, 0);
159 if(hwndButton == 0) {
160 dprintf(("RegisterSystemClasses failed!!"));
161 }
162 O32_SetClassLong(hwndButton, GCL_WNDPROC, (LONG)ButtonCallback);
163 }
164 if(O32_GetClassInfo(NULL, "LISTBOX", &wndclass)) {
165 dprintf(("Create LISTBOX System class"));
166 ListboxClass = new Win32WindowClass(ListboxCallback, "LISTBOX", hModule);
167 ListboxHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
168 hwndListbox = O32_CreateWindow("LISTBOX", "LISTBOX", 0, 0, 0, 0, 0, 0, 0, 0, 0);
169 if(hwndListbox == 0) {
170 dprintf(("RegisterSystemClasses failed!!"));
171 }
172 O32_SetClassLong(hwndListbox, GCL_WNDPROC, (LONG)ListboxCallback);
173 }
174 if(O32_GetClassInfo(NULL, "COMBOBOX", &wndclass)) {
175 dprintf(("Create COMBOBOX System class"));
176 ComboboxClass = new Win32WindowClass(ComboboxCallback, "COMBOBOX", hModule);
177 ComboboxHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
178 hwndCombobox = O32_CreateWindow("COMBOBOX", "COMBOBOX", 0, 0, 0, 0, 0, 0, 0, 0, 0);
179 if(hwndCombobox == 0) {
180 dprintf(("RegisterSystemClasses failed!!"));
181 }
182 O32_SetClassLong(hwndCombobox, GCL_WNDPROC, (LONG)ComboboxCallback);
183 }
184 if(O32_GetClassInfo(NULL, "EDIT", &wndclass)) {
185 dprintf(("Create EDIT System class"));
186 EditClass = new Win32WindowClass(EditCallback, "EDIT", hModule);
187 EditHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
188 hwndEdit = O32_CreateWindow("EDIT", "EDIT", 0, 0, 0, 0, 0, 0, 0, 0, 0);
189 if(hwndEdit == 0) {
190 dprintf(("RegisterSystemClasses failed!!"));
191 }
192 O32_SetClassLong(hwndEdit, GCL_WNDPROC, (LONG)EditCallback);
193 }
194 //TODO: This doens't work yet!! (need to create a normal window as parent)
195 if(O32_GetClassInfo(NULL, "MDICLIENT", &wndclass)) {
196 dprintf(("Create MDICLIENT System class"));
197 MdiClientClass = new Win32WindowClass(MdiClientCallback, "MDICLIENT", hModule);
198 MdiClientHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
199 hwndMdiClient = O32_CreateWindow("MDICLIENT", "MDICLIENT", WS_CHILD, 0, 0, 0, 0, hwndListbox, 0, 0, 0);
200 if(hwndMdiClient == 0) {
201 dprintf(("RegisterSystemClasses failed!!"));
202 }
203 O32_SetClassLong(hwndMdiClient, GCL_WNDPROC, (LONG)MdiClientCallback);
204 }
205 if(O32_GetClassInfo(NULL, "SCROLLBAR", &wndclass)) {
206 dprintf(("Create SCROLLBAR System class"));
207 ScrollbarClass = new Win32WindowClass(ScrollbarCallback, "SCROLLBAR", hModule);
208 ScrollbarHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
209 hwndScrollbar = O32_CreateWindow("SCROLLBAR", "SCROLLBAR", 0, 0, 0, 0, 0, 0, 0, 0, 0);
210 if(hwndScrollbar == 0) {
211 dprintf(("RegisterSystemClasses failed!!"));
212 }
213 O32_SetClassLong(hwndScrollbar, GCL_WNDPROC, (LONG)ScrollbarCallback);
214 }
215 if(O32_GetClassInfo(NULL, "STATIC", &wndclass)) {
216 dprintf(("Create STATIC System class"));
217 StaticClass = new Win32WindowClass(StaticCallback, "STATIC", hModule);
218 StaticHandler = (WNDPROC_O32)wndclass.lpfnWndProc;
219 hwndStatic = O32_CreateWindow("STATIC", "STATIC", 0, 0, 0, 0, 0, 0, 0, 0, 0);
220 if(hwndStatic == 0) {
221 dprintf(("RegisterSystemClasses failed!!"));
222 }
223 O32_SetClassLong(hwndStatic, GCL_WNDPROC, (LONG)StaticCallback);
224 }
225//TODO: More standard classes in win95/NT4?
226}
227//******************************************************************************
228//******************************************************************************
229void UnregisterSystemClasses()
230{
231 dprintf(("KERNEL32: UnregisterSystemClasses"));
232 if(hwndButton) O32_DestroyWindow(hwndButton);
233 if(hwndListbox) O32_DestroyWindow(hwndListbox);
234 if(hwndCombobox) O32_DestroyWindow(hwndCombobox);
235 if(hwndMdiClient) O32_DestroyWindow(hwndMdiClient);
236 if(hwndEdit) O32_DestroyWindow(hwndEdit);
237 if(hwndScrollbar) O32_DestroyWindow(hwndScrollbar);
238 if(hwndStatic) O32_DestroyWindow(hwndStatic);
239 if(ButtonClass) delete ButtonClass;
240 if(ListboxClass) delete ListboxClass;
241 if(EditClass) delete EditClass;
242 if(ComboboxClass) delete ComboboxClass;
243 if(MdiClientClass) delete MdiClientClass;
244 if(ScrollbarClass) delete ScrollbarClass;
245 if(StaticClass) delete StaticClass;
246 ButtonClass = NULL;
247 EditClass = NULL;
248 ListboxClass = NULL;
249 ComboboxClass = NULL;
250 MdiClientClass = NULL;
251 ScrollbarClass = NULL;
252 StaticClass = NULL;
253}
254//******************************************************************************
255//SvL: 18-7-'98: Moved here from user32.cpp
256//******************************************************************************
257ATOM WIN32API RegisterClassA(const WNDCLASSA *lpWndClass)
258{
259 ATOM rc;
260 WNDCLASSA wc;
261
262#ifdef DEBUG
263 WriteLog("USER32: RegisterClassA\n");
264 WriteLog("USER32: lpWndClass->style %X\n", lpWndClass->style);
265 WriteLog("USER32: lpWndClass->lpfnWndProc %X\n", lpWndClass->lpfnWndProc);
266 WriteLog("USER32: lpWndClass->cbClsExtra %X\n", lpWndClass->cbClsExtra);
267 WriteLog("USER32: lpWndClass->cbWndExtra %X\n", lpWndClass->cbWndExtra);
268 WriteLog("USER32: lpWndClass->hInstance %X\n", lpWndClass->hInstance);
269 WriteLog("USER32: lpWndClass->hIcon %X\n", lpWndClass->hIcon);
270 WriteLog("USER32: lpWndClass->hCursor %X\n", lpWndClass->hCursor);
271 WriteLog("USER32: lpWndClass->hbrBackground %X\n", lpWndClass->hbrBackground);
272 WriteLog("USER32: lpWndClass->lpszMenuName %X\n", lpWndClass->lpszMenuName);
273 if((int)lpWndClass->lpszClassName >> 16 == 0)
274 WriteLog("USER32: lpWndClass->lpszClassName %X\n", lpWndClass->lpszClassName);
275 else WriteLog("USER32: lpWndClass->lpszClassName %s\n", lpWndClass->lpszClassName);
276#endif
277 memcpy(&wc, lpWndClass, sizeof(WNDCLASSA));
278
279 if((int)wc.lpszMenuName >> 16 != 0) {//convert string name identifier to numeric id
280 dprintf(("USER32: lpszMenuName %s\n", wc.lpszMenuName));
281 *(int *)&wc.lpszMenuName = ConvertNameId(0, (char *)wc.lpszMenuName);
282 dprintf(("USER32: Menu id = %d\n", (int)wc.lpszMenuName));
283 }
284#ifdef DEBUG
285 if(wc.style & (CS_PARENTDC | CS_CLASSDC)) {
286 dprintf(("USER32: Class uses an unsupported style!!!\n"));
287 }
288#endif
289 //These are not supported by Open32
290 wc.style &= ~(CS_PARENTDC | CS_CLASSDC);
291
292 wc.lpfnWndProc = (WNDPROC)Win32WindowClass::GetOS2ClassCallback();
293 rc = O32_RegisterClass(&wc);
294 if(rc) {
295 Win32WindowClass *wndclass = new Win32WindowClass((WNDPROC)lpWndClass->lpfnWndProc, (LPSTR)wc.lpszClassName, wc.hInstance);
296 }
297 dprintf(("USER32: RegisterClass returned %d (%d)\n", rc, GetLastError()));
298 return(rc);
299}
300//******************************************************************************
301//SvL: 18-7-'98: Moved here from user32.cpp
302//******************************************************************************
303ATOM WIN32API RegisterClassExA(const WNDCLASSEXA *lpWndClass)
304{
305 ATOM rc;
306 WNDCLASSEXA wc;
307
308#ifdef DEBUG
309 WriteLog("USER32: lpWndClass->cbSize %X\n", lpWndClass->cbSize);
310 WriteLog("USER32: lpWndClass->style %X\n", lpWndClass->style);
311 WriteLog("USER32: lpWndClass->lpfnWndProc %X\n", lpWndClass->lpfnWndProc);
312 WriteLog("USER32: lpWndClass->cbClsExtra %X\n", lpWndClass->cbClsExtra);
313 WriteLog("USER32: lpWndClass->cbWndExtra %X\n", lpWndClass->cbWndExtra);
314 WriteLog("USER32: lpWndClass->hInstance %X\n", lpWndClass->hInstance);
315 WriteLog("USER32: lpWndClass->hIcon %X\n", lpWndClass->hIcon);
316 WriteLog("USER32: lpWndClass->hCursor %X\n", lpWndClass->hCursor);
317 WriteLog("USER32: lpWndClass->hbrBackground %X\n", lpWndClass->hbrBackground);
318 WriteLog("USER32: lpWndClass->lpszMenuName %X\n", lpWndClass->lpszMenuName);
319 if((int)lpWndClass->lpszClassName >> 16 == 0)
320 WriteLog("USER32: lpWndClass->lpszClassName %X\n", lpWndClass->lpszClassName);
321 else WriteLog("USER32: lpWndClass->lpszClassName %s\n", lpWndClass->lpszClassName);
322#endif
323 memcpy(&wc, lpWndClass, sizeof(WNDCLASSEXA));
324
325 if((int)wc.lpszMenuName >> 16 != 0) {//convert string name identifier to numeric id
326 dprintf(("USER32: lpszMenuName %s\n", wc.lpszMenuName));
327 *(int *)&wc.lpszMenuName = ConvertNameId(0, (char *)wc.lpszMenuName);
328 dprintf(("USER32: Menu id = %d\n", (int)wc.lpszMenuName));
329 }
330 if(wc.cbSize != sizeof(WNDCLASSEXA))
331 return(0);
332
333#ifdef DEBUG
334 if(wc.style & (CS_PARENTDC | CS_CLASSDC)) {
335 dprintf(("USER32: Class uses an unsupported style!!!\n"));
336 }
337#endif
338 //These are not supported by Open32
339 wc.style &= ~(CS_PARENTDC | CS_CLASSDC);
340
341 wc.lpfnWndProc = (WNDPROC)Win32WindowClass::GetOS2ClassCallback();
342
343 rc = O32_RegisterClass((WNDCLASSA *)&wc.style);
344 if(rc) {
345 Win32WindowClass *wndclass = new Win32WindowClass((WNDPROC)lpWndClass->lpfnWndProc, (LPSTR)wc.lpszClassName, wc.hInstance);
346 }
347#ifdef DEBUG
348 WriteLog("USER32: RegisterClassExA, not completely supported, returned %d\n", rc);
349 if(rc == 0)
350 WriteLog("USER32: GetLastError returned %X\n", GetLastError());
351
352#endif
353 return(rc);
354}
355//******************************************************************************
356//******************************************************************************
357WORD WIN32API RegisterClassW(const WNDCLASSW *lpwc)
358{
359 ATOM rc;
360 WNDCLASSA wclass;
361
362 dprintf(("RegisterClassW\n"));
363 memcpy(&wclass, lpwc, sizeof(WNDCLASSA));
364 if(wclass.lpszMenuName && ((int)wclass.lpszMenuName >> 16 != 0)) {
365 wclass.lpszMenuName = UnicodeToAsciiString((LPWSTR)lpwc->lpszMenuName);
366 }
367 if(wclass.lpszClassName && ((int)wclass.lpszClassName >> 16 != 0)) {
368 wclass.lpszClassName = UnicodeToAsciiString((LPWSTR)lpwc->lpszClassName);
369 }
370
371 rc = RegisterClassA(&wclass);
372
373 //TODO: Assuming RegisterClass doesn't mess up our structure
374 if(lpwc->lpszMenuName && ((int)lpwc->lpszMenuName >> 16 != 0)) {
375 FreeAsciiString((char *)wclass.lpszMenuName);
376 }
377 if(lpwc->lpszClassName && ((int)lpwc->lpszClassName >> 16 != 0)) {
378 FreeAsciiString((char *)wclass.lpszClassName);
379 }
380 return(rc);
381}
382//******************************************************************************
383//******************************************************************************
384ATOM WIN32API RegisterClassExW(CONST WNDCLASSEXW *lpwc)
385{
386 ATOM rc;
387 WNDCLASSEXA wclass;
388
389 dprintf(("RegisterClassExW\n"));
390 memcpy(&wclass, lpwc, sizeof(WNDCLASSEXA));
391 if(wclass.lpszMenuName && ((int)wclass.lpszMenuName >> 16 != 0)) {
392 wclass.lpszMenuName = UnicodeToAsciiString((LPWSTR)lpwc->lpszMenuName);
393 }
394 if(wclass.lpszClassName && ((int)wclass.lpszClassName >> 16 != 0)) {
395 wclass.lpszClassName = UnicodeToAsciiString((LPWSTR)lpwc->lpszClassName);
396 }
397
398 rc = RegisterClassExA(&wclass);
399
400 //TODO: Assuming RegisterClassEx doesn't mess up our structure
401 if(lpwc->lpszMenuName && ((int)lpwc->lpszMenuName >> 16 != 0)) {
402 FreeAsciiString((char *)wclass.lpszMenuName);
403 }
404 if(lpwc->lpszClassName && ((int)lpwc->lpszClassName >> 16 != 0)) {
405 FreeAsciiString((char *)wclass.lpszClassName);
406 }
407 return(rc);
408}
409//******************************************************************************
410//******************************************************************************
411BOOL WIN32API UnregisterClassA(LPCSTR lpszClassName, HINSTANCE hinst)
412{
413 BOOL rc;
414
415 Win32WindowClass::UnregisterClass(hinst, (LPSTR)lpszClassName);
416 rc = O32_UnregisterClass(lpszClassName, hinst);
417 dprintf(("USER32: OS2UnregisterClassA returned %d\n", rc));
418
419 //Spintest returns FALSE in dll termination, so pretend it succeeded
420 return(TRUE);
421}
422//******************************************************************************
423//******************************************************************************
424BOOL WIN32API UnregisterClassW(LPCWSTR lpszClassName, HINSTANCE hinst)
425{
426 char *astring = NULL;
427 BOOL rc;
428
429 dprintf(("USER32: OS2UnregisterClassW\n"));
430 if((int)lpszClassName >> 16 != 0) {
431 astring = UnicodeToAsciiString((LPWSTR)lpszClassName);
432 }
433 else astring = (char *)lpszClassName;
434
435 Win32WindowClass::UnregisterClass(hinst, (LPSTR)astring);
436 rc = O32_UnregisterClass(astring, hinst);
437 if((int)astring >> 16 != 0) {
438 FreeAsciiString(astring);
439 }
440 //Spintest returns FALSE in dll termination, so pretend it succeeded
441 return(TRUE);
442}
443//******************************************************************************
444//******************************************************************************
445BOOL WIN32API GetClassInfoA(HINSTANCE arg1, LPCSTR arg2, WNDCLASSA * arg3)
446{
447 BOOL rc;
448
449 dprintf(("USER32: OS2GetClassInfoA\n"));
450 rc = O32_GetClassInfo(arg1, arg2, (WNDCLASSA *)arg3);
451 if(rc == TRUE) {
452 arg3->lpfnWndProc = (WNDPROC)Win32WindowClass::GetClassCallback((LPSTR)arg2);
453 }
454 return(rc);
455}
456//******************************************************************************
457//******************************************************************************
458BOOL WIN32API GetClassInfoW(HINSTANCE hinst,
459 LPCWSTR lpszClass,
460 WNDCLASSW *lpwc)
461{
462 WNDCLASSA wclass;
463 BOOL rc;
464 char *szClass = NULL;
465
466 dprintf(("USER32: OS2GetClassInfoW\n"));
467 if((int)lpszClass >> 16 != 0) {
468 szClass = UnicodeToAsciiString((LPWSTR)lpszClass);
469 dprintf(("USER32: OS2GetClassInfoW %s\n", szClass));
470 }
471 else szClass = (char *)lpszClass;
472
473 rc = GetClassInfoA(hinst, szClass, &wclass);
474 if(rc == TRUE) {
475 memcpy(lpwc, &wclass, sizeof(WNDCLASSA));
476 //TODO: Memory leak (create class object at RegisterClass and delete it at UnregisterClass)
477 if(lpwc->lpszMenuName && ((int)lpwc->lpszMenuName >> 16 != 0)) {
478 lpwc->lpszMenuName = (LPCWSTR)malloc(strlen(wclass.lpszMenuName)*sizeof(WCHAR)+2);
479 AsciiToUnicode((char *)wclass.lpszMenuName, (LPWSTR)lpwc->lpszMenuName);
480 }
481 if(lpwc->lpszClassName && ((int)lpwc->lpszClassName >> 16 != 0)) {
482 lpwc->lpszClassName = (LPCWSTR)malloc(strlen(wclass.lpszClassName)*sizeof(WCHAR)+2);
483 AsciiToUnicode((char *)wclass.lpszClassName, (LPWSTR)lpwc->lpszClassName);
484 }
485 }
486 dprintf(("USER32: OS2GetClassInfoW returned %d\n", rc));
487 return(rc);
488}
489/****************************************************************************
490 * Name : BOOL WIN32API GetClassInfoExA
491 * Purpose : The GetClassInfoEx function retrieves information about a window
492 * class, including the handle of the small icon associated with the
493 * window class. GetClassInfo does not retrieve the handle of the small icon.
494 * Parameters: HINSTANCE hinst handle of application instance
495 * LPCTSTR lpszClass address of class name string
496 * LPWNDCLASSEX lpwcx address of structure for class data
497 * Variables :
498 * Result : If the function finds a matching class and successfully copies
499 * the data, the return value is TRUE;
500 * otherwise, it is FALSE.
501 * To get extended error information, call GetLastError.
502 * Remark : PH: does not obtain handle of the small icon
503 * Status : UNTESTED STUB
504 *
505 * Author : Patrick Haller [Thu, 1998/02/26 11:55]
506 *****************************************************************************/
507BOOL WIN32API GetClassInfoExA(HINSTANCE hInstance,
508 LPCTSTR lpszClass,
509 LPWNDCLASSEXA lpwcx)
510{
511 WNDCLASSA WndClass; /* structure for data transformation */
512 BOOL bResult; /* result of subsequent function calls */
513
514 dprintf(("USER32:GetClassInfoExA (%08xh,%s,%08x).\n",
515 hInstance,
516 lpszClass,
517 lpwcx));
518
519 /* convert the structures */
520 memcpy((PVOID)&WndClass,
521 (PVOID)&lpwcx->style,
522 sizeof(WndClass) );
523
524 bResult = GetClassInfoA(hInstance,
525 lpszClass,
526 (WNDCLASSA *)&WndClass);
527 if (bResult == TRUE)
528 {
529 /* convert data back to original structure */
530 memcpy((PVOID)&lpwcx->style,
531 (PVOID)&WndClass,
532 sizeof(WndClass) );
533 lpwcx->cbSize = sizeof(WNDCLASSEXA);
534 lpwcx->hIconSm = 0;
535 }
536
537 return (bResult);
538}
539/*****************************************************************************
540 * Name : BOOL WIN32API GetClassInfoExW
541 * Purpose : The GetClassInfoEx function retrieves information about a window
542 * class, including the handle of the small icon associated with the
543 * window class. GetClassInfo does not retrieve the handle of the small icon.
544 * Parameters: HINSTANCE hinst handle of application instance
545 * LPCWSTR lpszClass address of class name string
546 * LPWNDCLASSEX lpwcx address of structure for class data
547 * Variables :
548 * Result : If the function finds a matching class and successfully copies
549 * the data, the return value is TRUE;
550 * otherwise, it is FALSE.
551 * To get extended error information, call GetLastError.
552 * Remark : does not obtain handle of the small icon
553 * Status : UNTESTED STUB
554 *
555 * Author : Patrick Haller [Thu, 1998/02/26 11:55]
556 *****************************************************************************/
557BOOL WIN32API GetClassInfoExW(HINSTANCE hInstance,
558 LPCWSTR lpszClass,
559 LPWNDCLASSEXW lpwcx)
560{
561 WNDCLASSW WndClass; /* structure for data transformation */
562 BOOL bResult; /* result of subsequent function calls */
563
564 dprintf(("USER32:GetClassInfoExW (%08xh,%s,%08x).\n",
565 hInstance,
566 lpszClass,
567 lpwcx));
568
569 /* convert the structures */
570 memcpy((PVOID)&WndClass,
571 (PVOID)&lpwcx->style,
572 sizeof(WndClass) );
573
574 bResult = GetClassInfoW(hInstance,
575 (LPWSTR)lpszClass,
576 (WNDCLASSW *)&WndClass);
577 if (bResult == TRUE)
578 {
579 /* convert data back to original structure */
580 memcpy((PVOID)&lpwcx->style,
581 (PVOID)&WndClass,
582 sizeof(WndClass) );
583 lpwcx->cbSize = sizeof(WNDCLASSEXW);
584 lpwcx->hIconSm = 0;
585 }
586
587 return (bResult);
588}
589//******************************************************************************
590//TODO: Not complete (unsupported extension in WNDCLASSEXA/W, unsupported styles etc)
591//******************************************************************************
592LONG WIN32API GetClassLongA(HWND hwnd, int nIndex)
593{
594 DWORD rc;
595
596 dprintf(("USER32: OS2GetClassLongA\n"));
597 rc = O32_GetClassLong(hwnd, nIndex);
598 if(nIndex == GCL_WNDPROC) {
599 char szClass[128];
600 Win32WindowClass *wclass;
601
602 if(GetClassNameA(hwnd, szClass, sizeof(szClass))) {
603 wclass = Win32WindowClass::FindClass(szClass);
604 if(wclass) {
605 return (LONG)wclass->GetWinCallback();
606 }
607 }
608 dprintf(("GetClassLongA, class of window %X not found\n", hwnd));
609 return 0; //TODO: set last error
610 }
611 return rc;
612}
613//******************************************************************************
614//******************************************************************************
615LONG WIN32API GetClassLongW(HWND hwnd, int nIndex)
616{
617 dprintf(("USER32: OS2GetClassLongW\n"));
618 if(nIndex == GCL_MENUNAME) { //TODO
619 dprintf(("USER32: Class Menu name not implemented yet\n"));
620 }
621 // NOTE: This will not work as is (needs UNICODE support)
622 return GetClassLongA(hwnd, nIndex);
623}
624//******************************************************************************
625//******************************************************************************
626int WIN32API GetClassNameA( HWND arg1, LPSTR arg2, int arg3)
627{
628 dprintf(("USER32: OS2GetClassNameA\n"));
629 return O32_GetClassName(arg1, arg2, arg3);
630}
631//******************************************************************************
632//******************************************************************************
633int WIN32API GetClassNameW(HWND hwnd, LPWSTR lpClassName, int nMaxCount)
634{
635 char *astring = (char *)malloc(nMaxCount);
636 int rc;
637
638 dprintf(("USER32: OS2GetClassNameW\n"));
639 rc = GetClassNameA(hwnd, astring, nMaxCount);
640 AsciiToUnicode(astring, lpClassName);
641 free(astring);
642 return(rc);
643}
644//******************************************************************************
645//******************************************************************************
646WORD WIN32API GetClassWord( HWND arg1, int arg2)
647{
648 dprintf(("USER32: OS2GetClassWord\n"));
649 return O32_GetClassWord(arg1, arg2);
650}
651//******************************************************************************
652//******************************************************************************
653LONG WIN32API SetClassLongA(HWND hwnd, int nIndex, LONG lNewVal)
654{
655 DWORD rc;
656
657 dprintf(("USER32: OS2SetClassLongA\n"));
658 if(nIndex == GCL_WNDPROC) {
659 char szClass[128];
660 Win32WindowClass *wclass;
661
662 if(GetClassNameA(hwnd, szClass, sizeof(szClass))) {
663 wclass = Win32WindowClass::FindClass(szClass);
664 if(wclass) {
665 rc = (DWORD)wclass->GetWinCallback();
666 wclass->SetWinCallback((WNDPROC)lNewVal);
667 return rc;
668 }
669 }
670 dprintf(("SetClassLongA, class of window %X not found\n", hwnd));
671 return 0; //TODO: set last error
672 }
673 return O32_SetClassLong(hwnd, nIndex, lNewVal);
674}
675//******************************************************************************
676//******************************************************************************
677LONG WIN32API SetClassLongW( HWND arg1, int arg2, LONG arg3)
678{
679 dprintf(("USER32: OS2SetClassLongW\n"));
680 // NOTE: This will not work as is (needs UNICODE support)
681 return O32_SetClassLong(arg1, arg2, arg3);
682}
683//******************************************************************************
684//******************************************************************************
685WORD WIN32API SetClassWord( HWND arg1, int arg2, WORD arg3)
686{
687 dprintf(("USER32: OS2SetClassWord\n"));
688 return O32_SetClassWord(arg1, arg2, arg3);
689}
690//******************************************************************************
691//Win32WindowClass methods:
692//******************************************************************************
693Win32WindowClass::Win32WindowClass(WNDPROC pUserCallback, LPSTR id, HINSTANCE hinst)
694{
695 //Insert it in front of the rest
696 next = wndclasses;
697 wndclasses = this;
698 if((int)id >> 16 != 0) {
699 strcpy(className, id);
700 classAtom = 0;
701 }
702 else {
703 className[0] = 0;
704 classAtom = (DWORD)id;
705 }
706 this->hinst = hinst;
707
708 pWinCallback = pUserCallback;
709 dprintf(("Win32WindowClass::Win32WindowClass %d\n", id));
710}
711//******************************************************************************
712//******************************************************************************
713Win32WindowClass::~Win32WindowClass()
714{
715 Win32WindowClass *wndclass = Win32WindowClass::wndclasses;
716
717 if(wndclass == this) {
718 wndclasses = next;
719 }
720 else {
721 while(wndclass->next != NULL) {
722 if(wndclass->next == this) {
723 wndclass->next = next;
724 break;
725 }
726 wndclass = wndclass->next;
727 }
728 }
729}
730//******************************************************************************
731//******************************************************************************
732Win32WindowClass *Win32WindowClass::FindClass(LPSTR id)
733{
734 Win32WindowClass *wndclass = wndclasses;
735
736 if(wndclass == NULL) return(NULL);
737
738 if((int)id >> 16 != 0) {
739 if(stricmp(wndclass->className, id) == 0) {
740 return(wndclass);
741 }
742 else {
743 wndclass = wndclass->next;
744 while(wndclass != NULL) {
745 if(stricmp(wndclass->className, id) == 0) {
746 return(wndclass);
747 }
748 wndclass = wndclass->next;
749 }
750 }
751 }
752 else {
753 if(wndclass->classAtom == (DWORD)id) {
754 return(wndclass);
755 }
756 else {
757 wndclass = wndclass->next;
758 while(wndclass != NULL) {
759 if(wndclass->classAtom == (DWORD)id) {
760 return(wndclass);
761 }
762 wndclass = wndclass->next;
763 }
764 }
765 }
766 return(NULL);
767}
768//******************************************************************************
769//******************************************************************************
770void Win32WindowClass::UnregisterClass(HINSTANCE hinst, LPSTR id)
771{
772 Win32WindowClass *wndclass;
773
774 dprintf(("::UnregisterClass, destroy class %X!!\n", id));
775 wndclass = FindClass(id);
776 if(wndclass && wndclass->hinst == hinst) {
777 delete wndclass;
778 return;
779 }
780 dprintf(("::UnregisterClass, couldn't find class %X!!\n", id));
781}
782//******************************************************************************
783//******************************************************************************
784WNDPROC Win32WindowClass::GetClassCallback(HINSTANCE hinst, LPSTR id)
785{
786 Win32WindowClass *wndclass;
787
788 wndclass = FindClass(id);
789 if(wndclass && wndclass->hinst == hinst) {
790 return wndclass->pWinCallback;
791 }
792 dprintf(("::GetClassCallback, couldn't find class %X!!\n", id));
793 return(NULL);
794}
795//******************************************************************************
796//******************************************************************************
797WNDPROC Win32WindowClass::GetClassCallback(LPSTR id)
798{
799 Win32WindowClass *wndclass;
800
801 wndclass = FindClass(id);
802 if(wndclass) {
803 return wndclass->pWinCallback;
804 }
805 dprintf(("::GetClassCallback2, couldn't find class %X!!\n", id));
806 return(NULL);
807}
808//******************************************************************************
809//******************************************************************************
810WNDPROC_O32 Win32WindowClass::GetOS2ClassCallback()
811{
812 return OS2ToWinCallback;
813}
814//******************************************************************************
815//******************************************************************************
816LRESULT EXPENTRY_O32 OS2ToWinCallback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
817{
818 char szClass[128];
819 Win32WindowClass *wclass;
820 LRESULT rc;
821 DWORD dwStyle, dwExStyle;
822 HWND parentHwnd;
823 Win32WindowProc *window;
824
825 if(PostSpyMessage(hwnd, Msg, wParam, lParam) == FALSE)
826 dprintf(("OS2ToWinCallback %s for %x %x %x", GetMsgText(Msg), hwnd, wParam, lParam));
827
828 if(HkCBT::OS2HkCBTProc(hwnd, Msg, wParam, lParam) == TRUE) {//hook swallowed msg
829 return(0);
830 }
831
832 if(O32_GetClassName(hwnd, szClass, sizeof(szClass))) {
833 wclass = Win32WindowClass::FindClass(szClass);
834 if(wclass) {
835 switch(Msg)
836 {
837 case WM_CREATE://Open32 isn't sending WM_NCCREATE messages!!
838 window = Win32WindowProc::FindProc(hwnd, GetCurrentThreadId());
839 if(window) {
840 dprintf(("OS2ToWinCallback (class): New window object!"));
841 window->SetWindowHandle(hwnd);
842 }
843
844 if(wclass->GetWinCallback()(hwnd, WM_NCCREATE, 0, lParam) == 0) {
845 dprintf(("WM_NCCREATE returned FALSE\n"));
846 return(-1); //don't create window
847 }
848 //Send WM_CREATE message before notifying parent
849 rc = wclass->GetWinCallback()(hwnd, Msg, wParam, lParam);
850
851 NotifyParent(hwnd, WM_CREATE, wParam, lParam);
852 return(rc);
853
854 case WM_DESTROY: //nofity parent
855 case WM_LBUTTONDOWN:
856 case WM_MBUTTONDOWN:
857 case WM_RBUTTONDOWN:
858 NotifyParent(hwnd, Msg, wParam, lParam);
859 break;
860
861 case WM_KEYDOWN:
862 case WM_KEYUP:
863 case WM_CHAR: //SvL: Correct Open32 key mapping bug
864 //TODO: Not good enough, look at Wine
865 lParam = MapOEMToRealKey(wParam, lParam);
866 break;
867
868 case WM_MOUSEACTIVATE:
869 //Open32 sends an OS/2 window message for a button click
870 if(HIWORD(lParam) == 0x71) //WM_BUTTONCLICKFIRST
871 {
872 lParam = (WM_LBUTTONDOWN << 16) | LOWORD(lParam);
873 }
874 break;
875
876 case WM_ACTIVATE:
877 if(LOWORD(wParam) != WA_INACTIVE)
878 {
879 //EB: I think the problem is not a missing wm_erasebkgnd.
880 //Maybe some wrong flags in open32 during async repainting.
881 RECT rect;
882 HRGN hrgn;
883 HDC hdc = GetDC(hwnd);
884
885 // erase the dirty rect
886 GetUpdateRect(hwnd, &rect, TRUE);
887 hrgn = CreateRectRgnIndirect(&rect);
888 SelectClipRgn (hdc, hrgn);
889 DeleteObject (hrgn);
890 wclass->GetWinCallback()(hwnd, WM_ERASEBKGND, hdc, (LPARAM)&rect);
891 SelectClipRgn (hdc, NULL);
892 ReleaseDC(hwnd, hdc);
893 }
894 break;
895 }
896 return wclass->GetWinCallback()(hwnd, Msg, wParam, lParam);
897 }
898 }
899 dprintf(("OS2ToWinCallback: couldn't find class procedure of window %X\n", hwnd));
900 return(0);
901}
902//******************************************************************************
903//******************************************************************************
904LRESULT WIN32API WinToOS2Callback(HWND hwnd, UINT Msg, WPARAM wParam, LPARAM lParam)
905{
906 WNDPROC_O32 os2callback;
907
908 os2callback = (WNDPROC_O32)GetClassLongA(hwnd, GCL_WNDPROC);
909 if(os2callback) {
910 return os2callback(hwnd, Msg, wParam, lParam);
911 }
912 dprintf(("OS2ToWinCallback: window procedure == NULL!!\n"));
913 return(0);
914}
915//******************************************************************************
916//******************************************************************************
917Win32WindowClass *Win32WindowClass::wndclasses = NULL;
Note: See TracBrowser for help on using the repository browser.